mirror of
https://github.com/SchildiChat/SchildiChat-android.git
synced 2024-11-26 11:26:01 +03:00
Merge pull request #675 from vector-im/feature/cleanup
Cleanup ViewModel for code clarity
This commit is contained in:
commit
65b09ad4f0
93 changed files with 1072 additions and 709 deletions
|
@ -27,7 +27,12 @@ import im.vector.riotx.features.crypto.keysbackup.restore.KeysBackupRestoreFromP
|
|||
import im.vector.riotx.features.crypto.keysbackup.restore.KeysBackupRestoreSharedViewModel
|
||||
import im.vector.riotx.features.crypto.keysbackup.setup.KeysBackupSetupSharedViewModel
|
||||
import im.vector.riotx.features.crypto.verification.SasVerificationViewModel
|
||||
import im.vector.riotx.features.home.HomeSharedActionViewModel
|
||||
import im.vector.riotx.features.home.createdirect.CreateDirectRoomSharedActionViewModel
|
||||
import im.vector.riotx.features.home.room.detail.timeline.action.MessageSharedActionViewModel
|
||||
import im.vector.riotx.features.home.room.list.actions.RoomListQuickActionsSharedActionViewModel
|
||||
import im.vector.riotx.features.reactions.EmojiChooserViewModel
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectorySharedActionViewModel
|
||||
import im.vector.riotx.features.workers.signout.SignOutViewModel
|
||||
|
||||
@Module
|
||||
|
@ -82,4 +87,29 @@ interface ViewModelModule {
|
|||
@IntoMap
|
||||
@ViewModelKey(ConfigurationViewModel::class)
|
||||
fun bindConfigurationViewModel(viewModel: ConfigurationViewModel): ViewModel
|
||||
|
||||
@Binds
|
||||
@IntoMap
|
||||
@ViewModelKey(CreateDirectRoomSharedActionViewModel::class)
|
||||
fun bindCreateDirectRoomSharedActionViewModel(viewModel: CreateDirectRoomSharedActionViewModel): ViewModel
|
||||
|
||||
@Binds
|
||||
@IntoMap
|
||||
@ViewModelKey(HomeSharedActionViewModel::class)
|
||||
fun bindHomeSharedActionViewModel(viewModel: HomeSharedActionViewModel): ViewModel
|
||||
|
||||
@Binds
|
||||
@IntoMap
|
||||
@ViewModelKey(MessageSharedActionViewModel::class)
|
||||
fun bindMessageSharedActionViewModel(viewModel: MessageSharedActionViewModel): ViewModel
|
||||
|
||||
@Binds
|
||||
@IntoMap
|
||||
@ViewModelKey(RoomListQuickActionsSharedActionViewModel::class)
|
||||
fun bindRoomListQuickActionsSharedActionViewModel(viewModel: RoomListQuickActionsSharedActionViewModel): ViewModel
|
||||
|
||||
@Binds
|
||||
@IntoMap
|
||||
@ViewModelKey(RoomDirectorySharedActionViewModel::class)
|
||||
fun bindRoomDirectorySharedActionViewModel(viewModel: RoomDirectorySharedActionViewModel): ViewModel
|
||||
}
|
||||
|
|
|
@ -69,11 +69,19 @@ abstract class VectorBaseActivity : BaseMvRxActivity(), HasScreenInjector {
|
|||
@BindView(R.id.vector_coordinator_layout)
|
||||
var coordinatorLayout: CoordinatorLayout? = null
|
||||
|
||||
/* ==========================================================================================
|
||||
* View model
|
||||
* ========================================================================================== */
|
||||
|
||||
private lateinit var viewModelFactory: ViewModelProvider.Factory
|
||||
|
||||
protected val viewModelProvider
|
||||
get() = ViewModelProviders.of(this, viewModelFactory)
|
||||
|
||||
/* ==========================================================================================
|
||||
* DATA
|
||||
* ========================================================================================== */
|
||||
|
||||
protected lateinit var viewModelFactory: ViewModelProvider.Factory
|
||||
private lateinit var configurationViewModel: ConfigurationViewModel
|
||||
private lateinit var sessionListener: SessionListener
|
||||
protected lateinit var bugReporter: BugReporter
|
||||
|
@ -130,7 +138,7 @@ abstract class VectorBaseActivity : BaseMvRxActivity(), HasScreenInjector {
|
|||
supportFragmentManager.fragmentFactory = screenComponent.fragmentFactory()
|
||||
super.onCreate(savedInstanceState)
|
||||
viewModelFactory = screenComponent.viewModelFactory()
|
||||
configurationViewModel = ViewModelProviders.of(this, viewModelFactory).get(ConfigurationViewModel::class.java)
|
||||
configurationViewModel = viewModelProvider.get(ConfigurationViewModel::class.java)
|
||||
bugReporter = screenComponent.bugReporter()
|
||||
// Shake detector
|
||||
rageShake = screenComponent.rageShake()
|
||||
|
|
|
@ -21,6 +21,8 @@ import android.os.Bundle
|
|||
import android.os.Parcelable
|
||||
import android.widget.FrameLayout
|
||||
import androidx.annotation.CallSuper
|
||||
import androidx.lifecycle.ViewModelProvider
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import com.airbnb.mvrx.MvRx
|
||||
import com.airbnb.mvrx.MvRxView
|
||||
import com.airbnb.mvrx.MvRxViewModelStore
|
||||
|
@ -30,7 +32,7 @@ import com.google.android.material.bottomsheet.BottomSheetDialogFragment
|
|||
import im.vector.riotx.core.di.DaggerScreenComponent
|
||||
import im.vector.riotx.core.di.ScreenComponent
|
||||
import im.vector.riotx.core.utils.DimensionConverter
|
||||
import java.util.UUID
|
||||
import java.util.*
|
||||
|
||||
/**
|
||||
* Add MvRx capabilities to bottomsheetdialog (like BaseMvRxFragment)
|
||||
|
@ -42,6 +44,22 @@ abstract class VectorBaseBottomSheetDialogFragment : BottomSheetDialogFragment()
|
|||
private lateinit var screenComponent: ScreenComponent
|
||||
final override val mvrxViewId: String by lazy { mvrxPersistedViewId }
|
||||
|
||||
/* ==========================================================================================
|
||||
* View model
|
||||
* ========================================================================================== */
|
||||
|
||||
private lateinit var viewModelFactory: ViewModelProvider.Factory
|
||||
|
||||
protected val activityViewModelProvider
|
||||
get() = ViewModelProviders.of(requireActivity(), viewModelFactory)
|
||||
|
||||
protected val fragmentViewModelProvider
|
||||
get() = ViewModelProviders.of(this, viewModelFactory)
|
||||
|
||||
/* ==========================================================================================
|
||||
* BottomSheetBehavior
|
||||
* ========================================================================================== */
|
||||
|
||||
private var bottomSheetBehavior: BottomSheetBehavior<FrameLayout>? = null
|
||||
|
||||
val vectorBaseActivity: VectorBaseActivity by lazy {
|
||||
|
@ -52,6 +70,7 @@ abstract class VectorBaseBottomSheetDialogFragment : BottomSheetDialogFragment()
|
|||
|
||||
override fun onAttach(context: Context) {
|
||||
screenComponent = DaggerScreenComponent.factory().create(vectorBaseActivity.getVectorComponent(), vectorBaseActivity)
|
||||
viewModelFactory = screenComponent.viewModelFactory()
|
||||
super.onAttach(context)
|
||||
injectWith(screenComponent)
|
||||
}
|
||||
|
|
|
@ -25,6 +25,7 @@ import androidx.annotation.LayoutRes
|
|||
import androidx.annotation.MainThread
|
||||
import androidx.appcompat.widget.Toolbar
|
||||
import androidx.lifecycle.ViewModelProvider
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import butterknife.ButterKnife
|
||||
import butterknife.Unbinder
|
||||
import com.airbnb.mvrx.BaseMvRxFragment
|
||||
|
@ -51,10 +52,21 @@ abstract class VectorBaseFragment : BaseMvRxFragment(), HasScreenInjector {
|
|||
* Navigator
|
||||
* ========================================================================================== */
|
||||
|
||||
protected lateinit var viewModelFactory: ViewModelProvider.Factory
|
||||
protected lateinit var navigator: Navigator
|
||||
private lateinit var screenComponent: ScreenComponent
|
||||
|
||||
/* ==========================================================================================
|
||||
* View model
|
||||
* ========================================================================================== */
|
||||
|
||||
private lateinit var viewModelFactory: ViewModelProvider.Factory
|
||||
|
||||
protected val activityViewModelProvider
|
||||
get() = ViewModelProviders.of(requireActivity(), viewModelFactory)
|
||||
|
||||
protected val fragmentViewModelProvider
|
||||
get() = ViewModelProviders.of(this, viewModelFactory)
|
||||
|
||||
/* ==========================================================================================
|
||||
* Life cycle
|
||||
* ========================================================================================== */
|
||||
|
|
|
@ -14,11 +14,16 @@
|
|||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.home
|
||||
package im.vector.riotx.core.platform
|
||||
|
||||
import androidx.lifecycle.ViewModel
|
||||
import im.vector.riotx.core.utils.PublishDataSource
|
||||
import im.vector.riotx.core.utils.MutableDataSource
|
||||
import im.vector.riotx.core.utils.PublishDataSource
|
||||
|
||||
class HomeNavigationViewModel(private val source: MutableDataSource<HomeActivity.Navigation> = PublishDataSource())
|
||||
: ViewModel(), MutableDataSource<HomeActivity.Navigation> by source
|
||||
interface VectorSharedAction
|
||||
|
||||
/**
|
||||
* Parent class to handle navigation events, action events, or other any events
|
||||
*/
|
||||
open class VectorSharedActionViewModel<T : VectorSharedAction>(private val store: MutableDataSource<T> = PublishDataSource())
|
||||
: ViewModel(), MutableDataSource<T> by store
|
|
@ -23,7 +23,7 @@ import im.vector.riotx.core.utils.LiveEvent
|
|||
import io.reactivex.Observable
|
||||
import io.reactivex.Single
|
||||
|
||||
abstract class VectorViewModel<S : MvRxState>(initialState: S)
|
||||
abstract class VectorViewModel<S : MvRxState, A : VectorViewModelAction>(initialState: S)
|
||||
: BaseMvRxViewModel<S>(initialState, false) {
|
||||
|
||||
// Generic handling of any request error
|
||||
|
@ -52,4 +52,6 @@ abstract class VectorViewModel<S : MvRxState>(initialState: S)
|
|||
.onErrorReturn { Fail(it) }
|
||||
.doOnNext { setState { stateReducer(it) } }
|
||||
}
|
||||
|
||||
abstract fun handle(action: A)
|
||||
}
|
||||
|
|
|
@ -0,0 +1,24 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.core.platform
|
||||
|
||||
interface VectorViewModelAction
|
||||
|
||||
/**
|
||||
* To use when no action is associated to the ViewModel
|
||||
*/
|
||||
object EmptyAction : VectorViewModelAction
|
|
@ -21,7 +21,6 @@ import android.content.Intent
|
|||
import androidx.appcompat.app.AlertDialog
|
||||
import androidx.fragment.app.FragmentManager
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.extensions.addFragmentToBackstack
|
||||
import im.vector.riotx.core.extensions.observeEvent
|
||||
|
@ -43,7 +42,7 @@ class KeysBackupRestoreActivity : SimpleFragmentActivity() {
|
|||
|
||||
override fun initUiAndData() {
|
||||
super.initUiAndData()
|
||||
viewModel = ViewModelProviders.of(this, viewModelFactory).get(KeysBackupRestoreSharedViewModel::class.java)
|
||||
viewModel = viewModelProvider.get(KeysBackupRestoreSharedViewModel::class.java)
|
||||
viewModel.initSession(session)
|
||||
viewModel.keyVersionResult.observe(this, Observer { keyVersion ->
|
||||
|
||||
|
|
|
@ -22,7 +22,6 @@ import android.text.Editable
|
|||
import android.view.inputmethod.EditorInfo
|
||||
import android.widget.EditText
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import butterknife.BindView
|
||||
import butterknife.OnClick
|
||||
import butterknife.OnTextChanged
|
||||
|
@ -53,11 +52,8 @@ class KeysBackupRestoreFromKeyFragment @Inject constructor()
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
viewModel = ViewModelProviders.of(this, viewModelFactory).get(KeysBackupRestoreFromKeyViewModel::class.java)
|
||||
sharedViewModel = activity?.run {
|
||||
ViewModelProviders.of(this, viewModelFactory).get(KeysBackupRestoreSharedViewModel::class.java)
|
||||
} ?: throw Exception("Invalid Activity")
|
||||
|
||||
viewModel = fragmentViewModelProvider.get(KeysBackupRestoreFromKeyViewModel::class.java)
|
||||
sharedViewModel = activityViewModelProvider.get(KeysBackupRestoreSharedViewModel::class.java)
|
||||
mKeyTextEdit.setText(viewModel.recoveryCode.value)
|
||||
mKeyTextEdit.setOnEditorActionListener { _, actionId, _ ->
|
||||
if (actionId == EditorInfo.IME_ACTION_DONE) {
|
||||
|
|
|
@ -27,7 +27,6 @@ import android.widget.ImageView
|
|||
import android.widget.TextView
|
||||
import androidx.core.text.set
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import butterknife.BindView
|
||||
import butterknife.OnClick
|
||||
import butterknife.OnTextChanged
|
||||
|
@ -64,10 +63,8 @@ class KeysBackupRestoreFromPassphraseFragment @Inject constructor(): VectorBaseF
|
|||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
|
||||
viewModel = ViewModelProviders.of(this, viewModelFactory).get(KeysBackupRestoreFromPassphraseViewModel::class.java)
|
||||
sharedViewModel = activity?.run {
|
||||
ViewModelProviders.of(this, viewModelFactory).get(KeysBackupRestoreSharedViewModel::class.java)
|
||||
} ?: throw Exception("Invalid Activity")
|
||||
viewModel = fragmentViewModelProvider.get(KeysBackupRestoreFromPassphraseViewModel::class.java)
|
||||
sharedViewModel = activityViewModelProvider.get(KeysBackupRestoreSharedViewModel::class.java)
|
||||
|
||||
viewModel.passphraseErrorText.observe(viewLifecycleOwner, Observer { newValue ->
|
||||
mPassphraseInputLayout.error = newValue
|
||||
|
|
|
@ -17,7 +17,6 @@ package im.vector.riotx.features.crypto.keysbackup.restore
|
|||
|
||||
import android.os.Bundle
|
||||
import android.widget.TextView
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import butterknife.BindView
|
||||
import butterknife.OnClick
|
||||
import im.vector.riotx.R
|
||||
|
@ -38,9 +37,7 @@ class KeysBackupRestoreSuccessFragment @Inject constructor() : VectorBaseFragmen
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
sharedViewModel = activity?.run {
|
||||
ViewModelProviders.of(this, viewModelFactory).get(KeysBackupRestoreSharedViewModel::class.java)
|
||||
} ?: throw Exception("Invalid Activity")
|
||||
sharedViewModel = activityViewModelProvider.get(KeysBackupRestoreSharedViewModel::class.java)
|
||||
|
||||
sharedViewModel.importKeyResult?.let {
|
||||
val part1 = resources.getQuantityString(R.plurals.keys_backup_restore_success_description_part1,
|
||||
|
|
|
@ -0,0 +1,25 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.crypto.keysbackup.settings
|
||||
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class KeyBackupSettingsAction : VectorViewModelAction {
|
||||
object Init : KeyBackupSettingsAction()
|
||||
object GetKeyBackupTrust : KeyBackupSettingsAction()
|
||||
object DeleteKeyBackup : KeyBackupSettingsAction()
|
||||
}
|
|
@ -51,7 +51,7 @@ class KeysBackupManageActivity : SimpleFragmentActivity() {
|
|||
super.initUiAndData()
|
||||
if (supportFragmentManager.fragments.isEmpty()) {
|
||||
replaceFragment(R.id.container, KeysBackupSettingsFragment::class.java)
|
||||
viewModel.init()
|
||||
viewModel.handle(KeyBackupSettingsAction.Init)
|
||||
}
|
||||
|
||||
// Observe the deletion of keys backup
|
||||
|
|
|
@ -66,7 +66,7 @@ class KeysBackupSettingsFragment @Inject constructor(private val keysBackupSetti
|
|||
.setMessage(R.string.keys_backup_settings_delete_confirm_message)
|
||||
.setCancelable(false)
|
||||
.setPositiveButton(R.string.keys_backup_settings_delete_confirm_title) { _, _ ->
|
||||
viewModel.deleteCurrentBackup()
|
||||
viewModel.handle(KeyBackupSettingsAction.DeleteKeyBackup)
|
||||
}
|
||||
.setNegativeButton(R.string.cancel, null)
|
||||
.setCancelable(true)
|
||||
|
@ -75,10 +75,10 @@ class KeysBackupSettingsFragment @Inject constructor(private val keysBackupSetti
|
|||
}
|
||||
|
||||
override fun loadTrustData() {
|
||||
viewModel.getKeysBackupTrust()
|
||||
viewModel.handle(KeyBackupSettingsAction.GetKeyBackupTrust)
|
||||
}
|
||||
|
||||
override fun loadKeysBackupState() {
|
||||
viewModel.init()
|
||||
viewModel.handle(KeyBackupSettingsAction.Init)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -15,13 +15,7 @@
|
|||
*/
|
||||
package im.vector.riotx.features.crypto.keysbackup.settings
|
||||
|
||||
import com.airbnb.mvrx.ActivityViewModelContext
|
||||
import com.airbnb.mvrx.Fail
|
||||
import com.airbnb.mvrx.Loading
|
||||
import com.airbnb.mvrx.MvRxViewModelFactory
|
||||
import com.airbnb.mvrx.Success
|
||||
import com.airbnb.mvrx.Uninitialized
|
||||
import com.airbnb.mvrx.ViewModelContext
|
||||
import com.airbnb.mvrx.*
|
||||
import com.squareup.inject.assisted.Assisted
|
||||
import com.squareup.inject.assisted.AssistedInject
|
||||
import im.vector.matrix.android.api.MatrixCallback
|
||||
|
@ -34,8 +28,8 @@ import im.vector.riotx.core.platform.VectorViewModel
|
|||
|
||||
class KeysBackupSettingsViewModel @AssistedInject constructor(@Assisted initialState: KeysBackupSettingViewState,
|
||||
session: Session
|
||||
) : VectorViewModel<KeysBackupSettingViewState>(initialState),
|
||||
KeysBackupStateListener {
|
||||
) : VectorViewModel<KeysBackupSettingViewState, KeyBackupSettingsAction>(initialState),
|
||||
KeysBackupStateListener {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -64,11 +58,19 @@ class KeysBackupSettingsViewModel @AssistedInject constructor(@Assisted initialS
|
|||
getKeysBackupTrust()
|
||||
}
|
||||
|
||||
fun init() {
|
||||
override fun handle(action: KeyBackupSettingsAction) {
|
||||
when (action) {
|
||||
KeyBackupSettingsAction.Init -> init()
|
||||
KeyBackupSettingsAction.GetKeyBackupTrust -> getKeysBackupTrust()
|
||||
KeyBackupSettingsAction.DeleteKeyBackup -> deleteCurrentBackup()
|
||||
}
|
||||
}
|
||||
|
||||
private fun init() {
|
||||
keysBackupService.forceUsingLastVersion(object : MatrixCallback<Boolean> {})
|
||||
}
|
||||
|
||||
fun getKeysBackupTrust() = withState { state ->
|
||||
private fun getKeysBackupTrust() = withState { state ->
|
||||
val versionResult = keysBackupService.keysBackupVersion
|
||||
|
||||
if (state.keysBackupVersionTrust is Uninitialized && versionResult != null) {
|
||||
|
@ -116,7 +118,7 @@ class KeysBackupSettingsViewModel @AssistedInject constructor(@Assisted initialS
|
|||
getKeysBackupTrust()
|
||||
}
|
||||
|
||||
fun deleteCurrentBackup() {
|
||||
private fun deleteCurrentBackup() {
|
||||
val keysBackupService = keysBackupService
|
||||
|
||||
if (keysBackupService.currentBackupVersion != null) {
|
||||
|
@ -153,6 +155,6 @@ class KeysBackupSettingsViewModel @AssistedInject constructor(@Assisted initialS
|
|||
val currentBackupState = keysBackupService.state
|
||||
|
||||
return currentBackupState == KeysBackupState.Unknown
|
||||
|| currentBackupState == KeysBackupState.CheckingBackUpOnHomeserver
|
||||
|| currentBackupState == KeysBackupState.CheckingBackUpOnHomeserver
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,7 +21,6 @@ import androidx.appcompat.app.AlertDialog
|
|||
import androidx.core.view.isVisible
|
||||
import androidx.fragment.app.FragmentManager
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import im.vector.matrix.android.api.MatrixCallback
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.dialogs.ExportKeysDialog
|
||||
|
@ -43,7 +42,7 @@ class KeysBackupSetupActivity : SimpleFragmentActivity() {
|
|||
replaceFragment(R.id.container, KeysBackupSetupStep1Fragment::class.java)
|
||||
}
|
||||
|
||||
viewModel = ViewModelProviders.of(this, viewModelFactory).get(KeysBackupSetupSharedViewModel::class.java)
|
||||
viewModel = viewModelProvider.get(KeysBackupSetupSharedViewModel::class.java)
|
||||
viewModel.showManualExport.value = intent.getBooleanExtra(EXTRA_SHOW_MANUAL_EXPORT, false)
|
||||
viewModel.initSession(session)
|
||||
|
||||
|
|
|
@ -21,7 +21,6 @@ import android.view.View
|
|||
import android.widget.Button
|
||||
import android.widget.TextView
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import butterknife.BindView
|
||||
import butterknife.OnClick
|
||||
import im.vector.riotx.R
|
||||
|
@ -44,9 +43,7 @@ class KeysBackupSetupStep1Fragment @Inject constructor() : VectorBaseFragment()
|
|||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
|
||||
viewModel = activity?.run {
|
||||
ViewModelProviders.of(this, viewModelFactory).get(KeysBackupSetupSharedViewModel::class.java)
|
||||
} ?: throw Exception("Invalid Activity")
|
||||
viewModel = activityViewModelProvider.get(KeysBackupSetupSharedViewModel::class.java)
|
||||
|
||||
viewModel.showManualExport.observe(viewLifecycleOwner, Observer {
|
||||
val showOption = it ?: false
|
||||
|
|
|
@ -22,7 +22,6 @@ import android.view.inputmethod.EditorInfo
|
|||
import android.widget.EditText
|
||||
import android.widget.ImageView
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.transition.TransitionManager
|
||||
import butterknife.BindView
|
||||
import butterknife.OnClick
|
||||
|
@ -79,9 +78,7 @@ class KeysBackupSetupStep2Fragment @Inject constructor() : VectorBaseFragment()
|
|||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
|
||||
viewModel = activity?.run {
|
||||
ViewModelProviders.of(this, viewModelFactory).get(KeysBackupSetupSharedViewModel::class.java)
|
||||
} ?: throw Exception("Invalid Activity")
|
||||
viewModel = activityViewModelProvider.get(KeysBackupSetupSharedViewModel::class.java)
|
||||
|
||||
viewModel.shouldPromptOnBack = true
|
||||
bindViewToViewModel()
|
||||
|
|
|
@ -24,7 +24,6 @@ import android.widget.Toast
|
|||
import androidx.appcompat.app.AlertDialog
|
||||
import androidx.core.view.isVisible
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import arrow.core.Try
|
||||
import butterknife.BindView
|
||||
import butterknife.OnClick
|
||||
|
@ -58,9 +57,7 @@ class KeysBackupSetupStep3Fragment @Inject constructor() : VectorBaseFragment()
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
viewModel = activity?.run {
|
||||
ViewModelProviders.of(this, viewModelFactory).get(KeysBackupSetupSharedViewModel::class.java)
|
||||
} ?: throw Exception("Invalid Activity")
|
||||
viewModel = activityViewModelProvider.get(KeysBackupSetupSharedViewModel::class.java)
|
||||
|
||||
viewModel.shouldPromptOnBack = false
|
||||
|
||||
|
|
|
@ -21,7 +21,6 @@ import android.content.Intent
|
|||
import android.view.MenuItem
|
||||
import androidx.appcompat.app.AlertDialog
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import im.vector.matrix.android.api.session.crypto.sas.CancelCode
|
||||
import im.vector.matrix.android.api.session.crypto.sas.IncomingSasVerificationTransaction
|
||||
import im.vector.matrix.android.api.session.crypto.sas.OutgoingSasVerificationRequest
|
||||
|
@ -83,7 +82,7 @@ class SASVerificationActivity : SimpleFragmentActivity() {
|
|||
|
||||
override fun initUiAndData() {
|
||||
super.initUiAndData()
|
||||
viewModel = ViewModelProviders.of(this, viewModelFactory).get(SasVerificationViewModel::class.java)
|
||||
viewModel = viewModelProvider.get(SasVerificationViewModel::class.java)
|
||||
val transactionID: String? = intent.getStringExtra(EXTRA_TRANSACTION_ID)
|
||||
|
||||
if (isFirstCreation()) {
|
||||
|
|
|
@ -19,7 +19,6 @@ import android.os.Bundle
|
|||
import android.widget.ImageView
|
||||
import android.widget.TextView
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import butterknife.BindView
|
||||
import butterknife.OnClick
|
||||
import im.vector.matrix.android.api.session.crypto.sas.IncomingSasVerificationTransaction
|
||||
|
@ -51,9 +50,7 @@ class SASVerificationIncomingFragment @Inject constructor(
|
|||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
|
||||
viewModel = activity?.run {
|
||||
ViewModelProviders.of(this, viewModelFactory).get(SasVerificationViewModel::class.java)
|
||||
} ?: throw Exception("Invalid Activity")
|
||||
viewModel = activityViewModelProvider.get(SasVerificationViewModel::class.java)
|
||||
|
||||
otherUserDisplayNameTextView.text = viewModel.otherUser?.displayName ?: viewModel.otherUserId
|
||||
otherUserIdTextView.text = viewModel.otherUserId
|
||||
|
|
|
@ -21,7 +21,6 @@ import android.widget.TextView
|
|||
import androidx.core.view.isInvisible
|
||||
import androidx.core.view.isVisible
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import butterknife.BindView
|
||||
import butterknife.OnClick
|
||||
import im.vector.matrix.android.api.session.crypto.sas.IncomingSasVerificationTransaction
|
||||
|
@ -62,9 +61,7 @@ class SASVerificationShortCodeFragment @Inject constructor(): VectorBaseFragment
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
viewModel = activity?.run {
|
||||
ViewModelProviders.of(this, viewModelFactory).get(SasVerificationViewModel::class.java)
|
||||
} ?: throw Exception("Invalid Activity")
|
||||
viewModel = activityViewModelProvider.get(SasVerificationViewModel::class.java)
|
||||
|
||||
viewModel.transaction?.let {
|
||||
if (it.supportsEmoji()) {
|
||||
|
|
|
@ -23,7 +23,6 @@ import android.widget.TextView
|
|||
import androidx.core.view.isInvisible
|
||||
import androidx.core.view.isVisible
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.transition.TransitionManager
|
||||
import butterknife.BindView
|
||||
import butterknife.OnClick
|
||||
|
@ -53,7 +52,7 @@ class SASVerificationStartFragment @Inject constructor(): VectorBaseFragment() {
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
viewModel = ViewModelProviders.of(vectorBaseActivity, viewModelFactory).get(SasVerificationViewModel::class.java)
|
||||
viewModel = activityViewModelProvider.get(SasVerificationViewModel::class.java)
|
||||
viewModel.transactionState.observe(viewLifecycleOwner, Observer {
|
||||
val uxState = (viewModel.transaction as? OutgoingSasVerificationRequest)?.uxState
|
||||
when (uxState) {
|
||||
|
|
|
@ -16,7 +16,6 @@
|
|||
package im.vector.riotx.features.crypto.verification
|
||||
|
||||
import android.os.Bundle
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import butterknife.OnClick
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.platform.VectorBaseFragment
|
||||
|
@ -31,9 +30,7 @@ class SASVerificationVerifiedFragment @Inject constructor() : VectorBaseFragment
|
|||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
|
||||
viewModel = activity?.run {
|
||||
ViewModelProviders.of(this, viewModelFactory).get(SasVerificationViewModel::class.java)
|
||||
} ?: throw Exception("Invalid Activity")
|
||||
viewModel = activityViewModelProvider.get(SasVerificationViewModel::class.java)
|
||||
}
|
||||
|
||||
@OnClick(R.id.sas_verification_verified_done_button)
|
||||
|
|
|
@ -26,7 +26,6 @@ import androidx.core.view.GravityCompat
|
|||
import androidx.core.view.isVisible
|
||||
import androidx.drawerlayout.widget.DrawerLayout
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.di.ActiveSessionHolder
|
||||
import im.vector.riotx.core.di.ScreenComponent
|
||||
|
@ -47,13 +46,7 @@ import javax.inject.Inject
|
|||
|
||||
class HomeActivity : VectorBaseActivity(), ToolbarConfigurable {
|
||||
|
||||
// Supported navigation actions for this Activity
|
||||
sealed class Navigation {
|
||||
object OpenDrawer : Navigation()
|
||||
object OpenGroup : Navigation()
|
||||
}
|
||||
|
||||
private lateinit var navigationViewModel: HomeNavigationViewModel
|
||||
private lateinit var sharedActionViewModel: HomeSharedActionViewModel
|
||||
|
||||
@Inject lateinit var activeSessionHolder: ActiveSessionHolder
|
||||
@Inject lateinit var vectorUncaughtExceptionHandler: VectorUncaughtExceptionHandler
|
||||
|
@ -75,18 +68,19 @@ class HomeActivity : VectorBaseActivity(), ToolbarConfigurable {
|
|||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
FcmHelper.ensureFcmTokenIsRetrieved(this, pushManager)
|
||||
navigationViewModel = ViewModelProviders.of(this).get(HomeNavigationViewModel::class.java)
|
||||
sharedActionViewModel = viewModelProvider.get(HomeSharedActionViewModel::class.java)
|
||||
drawerLayout.addDrawerListener(drawerListener)
|
||||
if (isFirstCreation()) {
|
||||
replaceFragment(R.id.homeDetailFragmentContainer, LoadingFragment::class.java)
|
||||
replaceFragment(R.id.homeDrawerFragmentContainer, HomeDrawerFragment::class.java)
|
||||
}
|
||||
|
||||
navigationViewModel.observe()
|
||||
.subscribe { navigation ->
|
||||
when (navigation) {
|
||||
is Navigation.OpenDrawer -> drawerLayout.openDrawer(GravityCompat.START)
|
||||
is Navigation.OpenGroup -> {
|
||||
sharedActionViewModel
|
||||
.observe()
|
||||
.subscribe { sharedAction ->
|
||||
when (sharedAction) {
|
||||
is HomeActivitySharedAction.OpenDrawer -> drawerLayout.openDrawer(GravityCompat.START)
|
||||
is HomeActivitySharedAction.OpenGroup -> {
|
||||
drawerLayout.closeDrawer(GravityCompat.START)
|
||||
replaceFragment(R.id.homeDetailFragmentContainer, HomeDetailFragment::class.java)
|
||||
}
|
||||
|
@ -152,7 +146,7 @@ class HomeActivity : VectorBaseActivity(), ToolbarConfigurable {
|
|||
}
|
||||
|
||||
// Force remote backup state update to update the banner if needed
|
||||
ViewModelProviders.of(this).get(SignOutViewModel::class.java).refreshRemoteStateIfNeeded()
|
||||
viewModelProvider.get(SignOutViewModel::class.java).refreshRemoteStateIfNeeded()
|
||||
}
|
||||
|
||||
override fun configure(toolbar: Toolbar) {
|
||||
|
|
|
@ -0,0 +1,27 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.home
|
||||
|
||||
import im.vector.riotx.core.platform.VectorSharedAction
|
||||
|
||||
/**
|
||||
* Supported navigation actions for [HomeActivity]
|
||||
*/
|
||||
sealed class HomeActivitySharedAction : VectorSharedAction {
|
||||
object OpenDrawer : HomeActivitySharedAction()
|
||||
object OpenGroup : HomeActivitySharedAction()
|
||||
}
|
|
@ -0,0 +1,24 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.home
|
||||
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
import im.vector.riotx.features.home.room.list.RoomListFragment
|
||||
|
||||
sealed class HomeDetailAction : VectorViewModelAction {
|
||||
data class SwitchDisplayMode(val displayMode: RoomListFragment.DisplayMode) : HomeDetailAction()
|
||||
}
|
|
@ -20,7 +20,6 @@ import android.os.Bundle
|
|||
import android.view.LayoutInflater
|
||||
import androidx.core.view.forEachIndexed
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import com.airbnb.mvrx.fragmentViewModel
|
||||
import com.airbnb.mvrx.withState
|
||||
import com.google.android.material.bottomnavigation.BottomNavigationItemView
|
||||
|
@ -54,7 +53,7 @@ class HomeDetailFragment @Inject constructor(
|
|||
private val unreadCounterBadgeViews = arrayListOf<UnreadCounterBadgeView>()
|
||||
|
||||
private val viewModel: HomeDetailViewModel by fragmentViewModel()
|
||||
private lateinit var navigationViewModel: HomeNavigationViewModel
|
||||
private lateinit var sharedActionViewModel: HomeSharedActionViewModel
|
||||
|
||||
override fun getLayoutResId(): Int {
|
||||
return R.layout.fragment_home_detail
|
||||
|
@ -63,7 +62,7 @@ class HomeDetailFragment @Inject constructor(
|
|||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
|
||||
navigationViewModel = ViewModelProviders.of(requireActivity()).get(HomeNavigationViewModel::class.java)
|
||||
sharedActionViewModel = activityViewModelProvider.get(HomeSharedActionViewModel::class.java)
|
||||
|
||||
setupBottomNavigationView()
|
||||
setupToolbar()
|
||||
|
@ -91,9 +90,7 @@ class HomeDetailFragment @Inject constructor(
|
|||
private fun setupKeysBackupBanner() {
|
||||
// Keys backup banner
|
||||
// Use the SignOutViewModel, it observe the keys backup state and this is what we need here
|
||||
val model = ViewModelProviders.of(this, viewModelFactory).get(SignOutViewModel::class.java)
|
||||
|
||||
model.init(session)
|
||||
val model = fragmentViewModelProvider.get(SignOutViewModel::class.java)
|
||||
|
||||
model.keysBackupState.observe(viewLifecycleOwner, Observer { keysBackupState ->
|
||||
when (keysBackupState) {
|
||||
|
@ -129,7 +126,7 @@ class HomeDetailFragment @Inject constructor(
|
|||
}
|
||||
groupToolbar.title = ""
|
||||
groupToolbarAvatarImageView.setOnClickListener {
|
||||
navigationViewModel.post(HomeActivity.Navigation.OpenDrawer)
|
||||
sharedActionViewModel.post(HomeActivitySharedAction.OpenDrawer)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -141,7 +138,7 @@ class HomeDetailFragment @Inject constructor(
|
|||
R.id.bottom_action_rooms -> RoomListFragment.DisplayMode.ROOMS
|
||||
else -> RoomListFragment.DisplayMode.HOME
|
||||
}
|
||||
viewModel.switchDisplayMode(displayMode)
|
||||
viewModel.handle(HomeDetailAction.SwitchDisplayMode(displayMode))
|
||||
true
|
||||
}
|
||||
|
||||
|
|
|
@ -27,7 +27,6 @@ import im.vector.riotx.core.di.HasScreenInjector
|
|||
import im.vector.riotx.core.platform.VectorViewModel
|
||||
import im.vector.riotx.core.resources.StringProvider
|
||||
import im.vector.riotx.features.home.group.SelectedGroupDataSource
|
||||
import im.vector.riotx.features.home.room.list.RoomListFragment
|
||||
import im.vector.riotx.features.ui.UiStateRepository
|
||||
import io.reactivex.schedulers.Schedulers
|
||||
|
||||
|
@ -41,7 +40,7 @@ class HomeDetailViewModel @AssistedInject constructor(@Assisted initialState: Ho
|
|||
private val selectedGroupStore: SelectedGroupDataSource,
|
||||
private val homeRoomListStore: HomeRoomListDataSource,
|
||||
private val stringProvider: StringProvider)
|
||||
: VectorViewModel<HomeDetailViewState>(initialState) {
|
||||
: VectorViewModel<HomeDetailViewState, HomeDetailAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -70,13 +69,19 @@ class HomeDetailViewModel @AssistedInject constructor(@Assisted initialState: Ho
|
|||
observeRoomSummaries()
|
||||
}
|
||||
|
||||
fun switchDisplayMode(displayMode: RoomListFragment.DisplayMode) = withState { state ->
|
||||
if (state.displayMode != displayMode) {
|
||||
override fun handle(action: HomeDetailAction) {
|
||||
when (action) {
|
||||
is HomeDetailAction.SwitchDisplayMode -> handleSwitchDisplayMode(action)
|
||||
}
|
||||
}
|
||||
|
||||
private fun handleSwitchDisplayMode(action: HomeDetailAction.SwitchDisplayMode) = withState { state ->
|
||||
if (state.displayMode != action.displayMode) {
|
||||
setState {
|
||||
copy(displayMode = displayMode)
|
||||
copy(displayMode = action.displayMode)
|
||||
}
|
||||
|
||||
uiStateRepository.storeDisplayMode(displayMode)
|
||||
uiStateRepository.storeDisplayMode(action.displayMode)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,22 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.home
|
||||
|
||||
import im.vector.riotx.core.platform.VectorSharedActionViewModel
|
||||
import javax.inject.Inject
|
||||
|
||||
class HomeSharedActionViewModel @Inject constructor() : VectorSharedActionViewModel<HomeActivitySharedAction>()
|
|
@ -17,13 +17,13 @@
|
|||
package im.vector.riotx.features.home.createdirect
|
||||
|
||||
import im.vector.matrix.android.api.session.user.model.User
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class CreateDirectRoomActions {
|
||||
|
||||
object CreateRoomAndInviteSelectedUsers : CreateDirectRoomActions()
|
||||
data class FilterKnownUsers(val value: String) : CreateDirectRoomActions()
|
||||
data class SearchDirectoryUsers(val value: String) : CreateDirectRoomActions()
|
||||
object ClearFilterKnownUsers : CreateDirectRoomActions()
|
||||
data class SelectUser(val user: User) : CreateDirectRoomActions()
|
||||
data class RemoveSelectedUser(val user: User) : CreateDirectRoomActions()
|
||||
sealed class CreateDirectRoomAction : VectorViewModelAction {
|
||||
object CreateRoomAndInviteSelectedUsers : CreateDirectRoomAction()
|
||||
data class FilterKnownUsers(val value: String) : CreateDirectRoomAction()
|
||||
data class SearchDirectoryUsers(val value: String) : CreateDirectRoomAction()
|
||||
object ClearFilterKnownUsers : CreateDirectRoomAction()
|
||||
data class SelectUser(val user: User) : CreateDirectRoomAction()
|
||||
data class RemoveSelectedUser(val user: User) : CreateDirectRoomAction()
|
||||
}
|
|
@ -23,7 +23,6 @@ import android.content.Intent
|
|||
import android.os.Bundle
|
||||
import android.view.View
|
||||
import androidx.appcompat.app.AlertDialog
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import com.airbnb.mvrx.*
|
||||
import im.vector.matrix.android.api.session.room.failure.CreateRoomFailure
|
||||
import im.vector.riotx.R
|
||||
|
@ -38,14 +37,8 @@ import javax.inject.Inject
|
|||
|
||||
class CreateDirectRoomActivity : SimpleFragmentActivity() {
|
||||
|
||||
sealed class Navigation {
|
||||
object UsersDirectory : Navigation()
|
||||
object Close : Navigation()
|
||||
object Previous : Navigation()
|
||||
}
|
||||
|
||||
private val viewModel: CreateDirectRoomViewModel by viewModel()
|
||||
lateinit var navigationViewModel: CreateDirectRoomNavigationViewModel
|
||||
private lateinit var sharedActionViewModel: CreateDirectRoomSharedActionViewModel
|
||||
@Inject lateinit var createDirectRoomViewModelFactory: CreateDirectRoomViewModel.Factory
|
||||
@Inject lateinit var errorFormatter: ErrorFormatter
|
||||
|
||||
|
@ -57,13 +50,15 @@ class CreateDirectRoomActivity : SimpleFragmentActivity() {
|
|||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
toolbar.visibility = View.GONE
|
||||
navigationViewModel = ViewModelProviders.of(this, viewModelFactory).get(CreateDirectRoomNavigationViewModel::class.java)
|
||||
navigationViewModel.observe()
|
||||
.subscribe { navigation ->
|
||||
when (navigation) {
|
||||
is Navigation.UsersDirectory -> addFragmentToBackstack(R.id.container, CreateDirectRoomDirectoryUsersFragment::class.java)
|
||||
Navigation.Close -> finish()
|
||||
Navigation.Previous -> onBackPressed()
|
||||
sharedActionViewModel = viewModelProvider.get(CreateDirectRoomSharedActionViewModel::class.java)
|
||||
sharedActionViewModel
|
||||
.observe()
|
||||
.subscribe { sharedAction ->
|
||||
when (sharedAction) {
|
||||
CreateDirectRoomSharedAction.OpenUsersDirectory ->
|
||||
addFragmentToBackstack(R.id.container, CreateDirectRoomDirectoryUsersFragment::class.java)
|
||||
CreateDirectRoomSharedAction.Close -> finish()
|
||||
CreateDirectRoomSharedAction.GoBack -> onBackPressed()
|
||||
}
|
||||
}
|
||||
.disposeOnDestroy()
|
||||
|
|
|
@ -19,7 +19,6 @@ package im.vector.riotx.features.home.createdirect
|
|||
import android.content.Context
|
||||
import android.os.Bundle
|
||||
import android.view.inputmethod.InputMethodManager
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import com.airbnb.mvrx.activityViewModel
|
||||
import com.airbnb.mvrx.withState
|
||||
import com.jakewharton.rxbinding3.widget.textChanges
|
||||
|
@ -39,11 +38,11 @@ class CreateDirectRoomDirectoryUsersFragment @Inject constructor(
|
|||
|
||||
private val viewModel: CreateDirectRoomViewModel by activityViewModel()
|
||||
|
||||
private lateinit var navigationViewModel: CreateDirectRoomNavigationViewModel
|
||||
private lateinit var sharedActionViewModel: CreateDirectRoomSharedActionViewModel
|
||||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
navigationViewModel = ViewModelProviders.of(requireActivity(), viewModelFactory).get(CreateDirectRoomNavigationViewModel::class.java)
|
||||
sharedActionViewModel = activityViewModelProvider.get(CreateDirectRoomSharedActionViewModel::class.java)
|
||||
setupRecyclerView()
|
||||
setupSearchByMatrixIdView()
|
||||
setupCloseView()
|
||||
|
@ -60,7 +59,7 @@ class CreateDirectRoomDirectoryUsersFragment @Inject constructor(
|
|||
createDirectRoomSearchById
|
||||
.textChanges()
|
||||
.subscribe {
|
||||
viewModel.handle(CreateDirectRoomActions.SearchDirectoryUsers(it.toString()))
|
||||
viewModel.handle(CreateDirectRoomAction.SearchDirectoryUsers(it.toString()))
|
||||
}
|
||||
.disposeOnDestroy()
|
||||
createDirectRoomSearchById.requestFocus()
|
||||
|
@ -70,7 +69,7 @@ class CreateDirectRoomDirectoryUsersFragment @Inject constructor(
|
|||
|
||||
private fun setupCloseView() {
|
||||
createDirectRoomClose.setOnClickListener {
|
||||
navigationViewModel.post(CreateDirectRoomActivity.Navigation.Previous)
|
||||
sharedActionViewModel.post(CreateDirectRoomSharedAction.GoBack)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -80,12 +79,12 @@ class CreateDirectRoomDirectoryUsersFragment @Inject constructor(
|
|||
|
||||
override fun onItemClick(user: User) {
|
||||
view?.hideKeyboard()
|
||||
viewModel.handle(CreateDirectRoomActions.SelectUser(user))
|
||||
navigationViewModel.post(CreateDirectRoomActivity.Navigation.Previous)
|
||||
viewModel.handle(CreateDirectRoomAction.SelectUser(user))
|
||||
sharedActionViewModel.post(CreateDirectRoomSharedAction.GoBack)
|
||||
}
|
||||
|
||||
override fun retryDirectoryUsersRequest() {
|
||||
val currentSearch = createDirectRoomSearchById.text.toString()
|
||||
viewModel.handle(CreateDirectRoomActions.SearchDirectoryUsers(currentSearch))
|
||||
viewModel.handle(CreateDirectRoomAction.SearchDirectoryUsers(currentSearch))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -23,7 +23,6 @@ import android.view.Menu
|
|||
import android.view.MenuItem
|
||||
import android.widget.ScrollView
|
||||
import androidx.core.view.size
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import com.airbnb.mvrx.activityViewModel
|
||||
import com.airbnb.mvrx.withState
|
||||
import com.google.android.material.chip.Chip
|
||||
|
@ -49,11 +48,11 @@ class CreateDirectRoomKnownUsersFragment @Inject constructor(
|
|||
override fun getMenuRes() = R.menu.vector_create_direct_room
|
||||
|
||||
private val viewModel: CreateDirectRoomViewModel by activityViewModel()
|
||||
private lateinit var navigationViewModel: CreateDirectRoomNavigationViewModel
|
||||
private lateinit var sharedActionViewModel: CreateDirectRoomSharedActionViewModel
|
||||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
navigationViewModel = ViewModelProviders.of(requireActivity(), viewModelFactory).get(CreateDirectRoomNavigationViewModel::class.java)
|
||||
sharedActionViewModel = activityViewModelProvider.get(CreateDirectRoomSharedActionViewModel::class.java)
|
||||
vectorBaseActivity.setSupportActionBar(createDirectRoomToolbar)
|
||||
setupRecyclerView()
|
||||
setupFilterView()
|
||||
|
@ -79,7 +78,7 @@ class CreateDirectRoomKnownUsersFragment @Inject constructor(
|
|||
override fun onOptionsItemSelected(item: MenuItem): Boolean {
|
||||
return when (item.itemId) {
|
||||
R.id.action_create_direct_room -> {
|
||||
viewModel.handle(CreateDirectRoomActions.CreateRoomAndInviteSelectedUsers)
|
||||
viewModel.handle(CreateDirectRoomAction.CreateRoomAndInviteSelectedUsers)
|
||||
true
|
||||
}
|
||||
else ->
|
||||
|
@ -89,7 +88,7 @@ class CreateDirectRoomKnownUsersFragment @Inject constructor(
|
|||
|
||||
private fun setupAddByMatrixIdView() {
|
||||
addByMatrixId.setOnClickListener {
|
||||
navigationViewModel.post(CreateDirectRoomActivity.Navigation.UsersDirectory)
|
||||
sharedActionViewModel.post(CreateDirectRoomSharedAction.OpenUsersDirectory)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -108,9 +107,9 @@ class CreateDirectRoomKnownUsersFragment @Inject constructor(
|
|||
.subscribe { text ->
|
||||
val filterValue = text.trim()
|
||||
val action = if (filterValue.isBlank()) {
|
||||
CreateDirectRoomActions.ClearFilterKnownUsers
|
||||
CreateDirectRoomAction.ClearFilterKnownUsers
|
||||
} else {
|
||||
CreateDirectRoomActions.FilterKnownUsers(filterValue.toString())
|
||||
CreateDirectRoomAction.FilterKnownUsers(filterValue.toString())
|
||||
}
|
||||
viewModel.handle(action)
|
||||
}
|
||||
|
@ -157,7 +156,7 @@ class CreateDirectRoomKnownUsersFragment @Inject constructor(
|
|||
chip.isCloseIconVisible = true
|
||||
chipGroup.addView(chip)
|
||||
chip.setOnCloseIconClickListener {
|
||||
viewModel.handle(CreateDirectRoomActions.RemoveSelectedUser(user))
|
||||
viewModel.handle(CreateDirectRoomAction.RemoveSelectedUser(user))
|
||||
}
|
||||
chipGroupScrollView.post {
|
||||
chipGroupScrollView.fullScroll(ScrollView.FOCUS_DOWN)
|
||||
|
@ -166,6 +165,6 @@ class CreateDirectRoomKnownUsersFragment @Inject constructor(
|
|||
|
||||
override fun onItemClick(user: User) {
|
||||
view?.hideKeyboard()
|
||||
viewModel.handle(CreateDirectRoomActions.SelectUser(user))
|
||||
viewModel.handle(CreateDirectRoomAction.SelectUser(user))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,25 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.home.createdirect
|
||||
|
||||
import im.vector.riotx.core.platform.VectorSharedAction
|
||||
|
||||
sealed class CreateDirectRoomSharedAction : VectorSharedAction {
|
||||
object OpenUsersDirectory : CreateDirectRoomSharedAction()
|
||||
object Close : CreateDirectRoomSharedAction()
|
||||
object GoBack : CreateDirectRoomSharedAction()
|
||||
}
|
|
@ -16,9 +16,7 @@
|
|||
|
||||
package im.vector.riotx.features.home.createdirect
|
||||
|
||||
import androidx.lifecycle.ViewModel
|
||||
import im.vector.riotx.core.utils.PublishDataSource
|
||||
import im.vector.riotx.core.utils.MutableDataSource
|
||||
import im.vector.riotx.core.platform.VectorSharedActionViewModel
|
||||
import javax.inject.Inject
|
||||
|
||||
class CreateDirectRoomNavigationViewModel(private val dataSource: MutableDataSource<CreateDirectRoomActivity.Navigation> = PublishDataSource())
|
||||
: ViewModel(), MutableDataSource<CreateDirectRoomActivity.Navigation> by dataSource
|
||||
class CreateDirectRoomSharedActionViewModel @Inject constructor() : VectorSharedActionViewModel<CreateDirectRoomSharedAction>()
|
|
@ -51,7 +51,7 @@ data class SelectUserAction(
|
|||
class CreateDirectRoomViewModel @AssistedInject constructor(@Assisted
|
||||
initialState: CreateDirectRoomViewState,
|
||||
private val session: Session)
|
||||
: VectorViewModel<CreateDirectRoomViewState>(initialState) {
|
||||
: VectorViewModel<CreateDirectRoomViewState, CreateDirectRoomAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -79,14 +79,14 @@ class CreateDirectRoomViewModel @AssistedInject constructor(@Assisted
|
|||
observeDirectoryUsers()
|
||||
}
|
||||
|
||||
fun handle(action: CreateDirectRoomActions) {
|
||||
override fun handle(action: CreateDirectRoomAction) {
|
||||
when (action) {
|
||||
is CreateDirectRoomActions.CreateRoomAndInviteSelectedUsers -> createRoomAndInviteSelectedUsers()
|
||||
is CreateDirectRoomActions.FilterKnownUsers -> knownUsersFilter.accept(Option.just(action.value))
|
||||
is CreateDirectRoomActions.ClearFilterKnownUsers -> knownUsersFilter.accept(Option.empty())
|
||||
is CreateDirectRoomActions.SearchDirectoryUsers -> directoryUsersSearch.accept(action.value)
|
||||
is CreateDirectRoomActions.SelectUser -> handleSelectUser(action)
|
||||
is CreateDirectRoomActions.RemoveSelectedUser -> handleRemoveSelectedUser(action)
|
||||
is CreateDirectRoomAction.CreateRoomAndInviteSelectedUsers -> createRoomAndInviteSelectedUsers()
|
||||
is CreateDirectRoomAction.FilterKnownUsers -> knownUsersFilter.accept(Option.just(action.value))
|
||||
is CreateDirectRoomAction.ClearFilterKnownUsers -> knownUsersFilter.accept(Option.empty())
|
||||
is CreateDirectRoomAction.SearchDirectoryUsers -> directoryUsersSearch.accept(action.value)
|
||||
is CreateDirectRoomAction.SelectUser -> handleSelectUser(action)
|
||||
is CreateDirectRoomAction.RemoveSelectedUser -> handleRemoveSelectedUser(action)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -105,14 +105,14 @@ class CreateDirectRoomViewModel @AssistedInject constructor(@Assisted
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleRemoveSelectedUser(action: CreateDirectRoomActions.RemoveSelectedUser) = withState { state ->
|
||||
private fun handleRemoveSelectedUser(action: CreateDirectRoomAction.RemoveSelectedUser) = withState { state ->
|
||||
val index = state.selectedUsers.indexOfFirst { it.userId == action.user.userId }
|
||||
val selectedUsers = state.selectedUsers.minus(action.user)
|
||||
setState { copy(selectedUsers = selectedUsers) }
|
||||
_selectUserEvent.postLiveEvent(SelectUserAction(action.user, false, index))
|
||||
}
|
||||
|
||||
private fun handleSelectUser(action: CreateDirectRoomActions.SelectUser) = withState { state ->
|
||||
private fun handleSelectUser(action: CreateDirectRoomAction.SelectUser) = withState { state ->
|
||||
// Reset the filter asap
|
||||
directoryUsersSearch.accept("")
|
||||
val isAddOperation: Boolean
|
||||
|
|
|
@ -17,8 +17,8 @@
|
|||
package im.vector.riotx.features.home.group
|
||||
|
||||
import im.vector.matrix.android.api.session.group.model.GroupSummary
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class GroupListActions {
|
||||
|
||||
data class SelectGroup(val groupSummary: GroupSummary) : GroupListActions()
|
||||
sealed class GroupListAction : VectorViewModelAction {
|
||||
data class SelectGroup(val groupSummary: GroupSummary) : GroupListAction()
|
||||
}
|
|
@ -17,7 +17,6 @@
|
|||
package im.vector.riotx.features.home.group
|
||||
|
||||
import android.os.Bundle
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import com.airbnb.mvrx.Incomplete
|
||||
import com.airbnb.mvrx.Success
|
||||
import com.airbnb.mvrx.fragmentViewModel
|
||||
|
@ -26,8 +25,8 @@ import im.vector.riotx.R
|
|||
import im.vector.riotx.core.extensions.observeEvent
|
||||
import im.vector.riotx.core.platform.StateView
|
||||
import im.vector.riotx.core.platform.VectorBaseFragment
|
||||
import im.vector.riotx.features.home.HomeActivity
|
||||
import im.vector.riotx.features.home.HomeNavigationViewModel
|
||||
import im.vector.riotx.features.home.HomeSharedActionViewModel
|
||||
import im.vector.riotx.features.home.HomeActivitySharedAction
|
||||
import kotlinx.android.synthetic.main.fragment_group_list.*
|
||||
import javax.inject.Inject
|
||||
|
||||
|
@ -36,20 +35,20 @@ class GroupListFragment @Inject constructor(
|
|||
private val groupController: GroupSummaryController
|
||||
) : VectorBaseFragment(), GroupSummaryController.Callback {
|
||||
|
||||
private lateinit var navigationViewModel: HomeNavigationViewModel
|
||||
private lateinit var sharedActionViewModel: HomeSharedActionViewModel
|
||||
private val viewModel: GroupListViewModel by fragmentViewModel()
|
||||
|
||||
override fun getLayoutResId() = R.layout.fragment_group_list
|
||||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
navigationViewModel = ViewModelProviders.of(requireActivity()).get(HomeNavigationViewModel::class.java)
|
||||
sharedActionViewModel = activityViewModelProvider.get(HomeSharedActionViewModel::class.java)
|
||||
groupController.callback = this
|
||||
stateView.contentView = groupListEpoxyRecyclerView
|
||||
groupListEpoxyRecyclerView.setController(groupController)
|
||||
viewModel.subscribe { renderState(it) }
|
||||
viewModel.openGroupLiveData.observeEvent(this) {
|
||||
navigationViewModel.post(HomeActivity.Navigation.OpenGroup)
|
||||
sharedActionViewModel.post(HomeActivitySharedAction.OpenGroup)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -62,6 +61,6 @@ class GroupListFragment @Inject constructor(
|
|||
}
|
||||
|
||||
override fun onGroupSelected(groupSummary: GroupSummary) {
|
||||
viewModel.accept(GroupListActions.SelectGroup(groupSummary))
|
||||
viewModel.handle(GroupListAction.SelectGroup(groupSummary))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -42,7 +42,7 @@ class GroupListViewModel @AssistedInject constructor(@Assisted initialState: Gro
|
|||
private val selectedGroupStore: SelectedGroupDataSource,
|
||||
private val session: Session,
|
||||
private val stringProvider: StringProvider
|
||||
) : VectorViewModel<GroupListViewState>(initialState) {
|
||||
) : VectorViewModel<GroupListViewState, GroupListAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -81,15 +81,15 @@ class GroupListViewModel @AssistedInject constructor(@Assisted initialState: Gro
|
|||
}
|
||||
}
|
||||
|
||||
fun accept(action: GroupListActions) {
|
||||
override fun handle(action: GroupListAction) {
|
||||
when (action) {
|
||||
is GroupListActions.SelectGroup -> handleSelectGroup(action)
|
||||
is GroupListAction.SelectGroup -> handleSelectGroup(action)
|
||||
}
|
||||
}
|
||||
|
||||
// PRIVATE METHODS *****************************************************************************
|
||||
|
||||
private fun handleSelectGroup(action: GroupListActions.SelectGroup) = withState { state ->
|
||||
private fun handleSelectGroup(action: GroupListAction.SelectGroup) = withState { state ->
|
||||
if (state.selectedGroup?.groupId != action.groupSummary.groupId) {
|
||||
setState { copy(selectedGroup = action.groupSummary) }
|
||||
}
|
||||
|
|
|
@ -21,44 +21,44 @@ import im.vector.matrix.android.api.session.events.model.Event
|
|||
import im.vector.matrix.android.api.session.room.model.message.MessageFileContent
|
||||
import im.vector.matrix.android.api.session.room.timeline.Timeline
|
||||
import im.vector.matrix.android.api.session.room.timeline.TimelineEvent
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class RoomDetailActions {
|
||||
sealed class RoomDetailAction : VectorViewModelAction {
|
||||
data class SaveDraft(val draft: String) : RoomDetailAction()
|
||||
data class SendMessage(val text: String, val autoMarkdown: Boolean) : RoomDetailAction()
|
||||
data class SendMedia(val attachments: List<ContentAttachmentData>) : RoomDetailAction()
|
||||
data class TimelineEventTurnsVisible(val event: TimelineEvent) : RoomDetailAction()
|
||||
data class TimelineEventTurnsInvisible(val event: TimelineEvent) : RoomDetailAction()
|
||||
data class LoadMoreTimelineEvents(val direction: Timeline.Direction) : RoomDetailAction()
|
||||
data class SendReaction(val targetEventId: String, val reaction: String) : RoomDetailAction()
|
||||
data class UndoReaction(val targetEventId: String, val reaction: String, val reason: String? = "") : RoomDetailAction()
|
||||
data class RedactAction(val targetEventId: String, val reason: String? = "") : RoomDetailAction()
|
||||
data class UpdateQuickReactAction(val targetEventId: String, val selectedReaction: String, val add: Boolean) : RoomDetailAction()
|
||||
data class NavigateToEvent(val eventId: String, val highlight: Boolean) : RoomDetailAction()
|
||||
data class SetReadMarkerAction(val eventId: String) : RoomDetailAction()
|
||||
object MarkAllAsRead : RoomDetailAction()
|
||||
data class DownloadFile(val eventId: String, val messageFileContent: MessageFileContent) : RoomDetailAction()
|
||||
data class HandleTombstoneEvent(val event: Event) : RoomDetailAction()
|
||||
object AcceptInvite : RoomDetailAction()
|
||||
object RejectInvite : RoomDetailAction()
|
||||
|
||||
data class SaveDraft(val draft: String) : RoomDetailActions()
|
||||
data class SendMessage(val text: String, val autoMarkdown: Boolean) : RoomDetailActions()
|
||||
data class SendMedia(val attachments: List<ContentAttachmentData>) : RoomDetailActions()
|
||||
data class TimelineEventTurnsVisible(val event: TimelineEvent) : RoomDetailActions()
|
||||
data class TimelineEventTurnsInvisible(val event: TimelineEvent) : RoomDetailActions()
|
||||
data class LoadMoreTimelineEvents(val direction: Timeline.Direction) : RoomDetailActions()
|
||||
data class SendReaction(val targetEventId: String, val reaction: String) : RoomDetailActions()
|
||||
data class UndoReaction(val targetEventId: String, val reaction: String, val reason: String? = "") : RoomDetailActions()
|
||||
data class RedactAction(val targetEventId: String, val reason: String? = "") : RoomDetailActions()
|
||||
data class UpdateQuickReactAction(val targetEventId: String, val selectedReaction: String, val add: Boolean) : RoomDetailActions()
|
||||
data class NavigateToEvent(val eventId: String, val highlight: Boolean) : RoomDetailActions()
|
||||
data class SetReadMarkerAction(val eventId: String) : RoomDetailActions()
|
||||
object MarkAllAsRead : RoomDetailActions()
|
||||
data class DownloadFile(val eventId: String, val messageFileContent: MessageFileContent) : RoomDetailActions()
|
||||
data class HandleTombstoneEvent(val event: Event) : RoomDetailActions()
|
||||
object AcceptInvite : RoomDetailActions()
|
||||
object RejectInvite : RoomDetailActions()
|
||||
data class EnterEditMode(val eventId: String, val draft: String) : RoomDetailAction()
|
||||
data class EnterQuoteMode(val eventId: String, val draft: String) : RoomDetailAction()
|
||||
data class EnterReplyMode(val eventId: String, val draft: String) : RoomDetailAction()
|
||||
data class ExitSpecialMode(val draft: String) : RoomDetailAction()
|
||||
|
||||
data class EnterEditMode(val eventId: String, val draft: String) : RoomDetailActions()
|
||||
data class EnterQuoteMode(val eventId: String, val draft: String) : RoomDetailActions()
|
||||
data class EnterReplyMode(val eventId: String, val draft: String) : RoomDetailActions()
|
||||
data class ExitSpecialMode(val draft: String) : RoomDetailActions()
|
||||
|
||||
data class ResendMessage(val eventId: String) : RoomDetailActions()
|
||||
data class RemoveFailedEcho(val eventId: String) : RoomDetailActions()
|
||||
data class ResendMessage(val eventId: String) : RoomDetailAction()
|
||||
data class RemoveFailedEcho(val eventId: String) : RoomDetailAction()
|
||||
|
||||
data class ReportContent(
|
||||
val eventId: String,
|
||||
val senderId: String?,
|
||||
val reason: String,
|
||||
val spam: Boolean = false,
|
||||
val inappropriate: Boolean = false) : RoomDetailActions()
|
||||
val inappropriate: Boolean = false) : RoomDetailAction()
|
||||
|
||||
data class IgnoreUser(val userId: String?) : RoomDetailActions()
|
||||
data class IgnoreUser(val userId: String?) : RoomDetailAction()
|
||||
|
||||
object ClearSendQueue : RoomDetailActions()
|
||||
object ResendAll : RoomDetailActions()
|
||||
object ClearSendQueue : RoomDetailAction()
|
||||
object ResendAll : RoomDetailAction()
|
||||
}
|
|
@ -40,7 +40,6 @@ import androidx.core.content.ContextCompat
|
|||
import androidx.core.util.Pair
|
||||
import androidx.core.view.ViewCompat
|
||||
import androidx.core.view.forEach
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.recyclerview.widget.ItemTouchHelper
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
|
@ -91,15 +90,15 @@ import im.vector.riotx.features.home.AvatarRenderer
|
|||
import im.vector.riotx.features.home.NavigateToRoomInterceptor
|
||||
import im.vector.riotx.features.home.PermalinkHandler
|
||||
import im.vector.riotx.features.home.getColorFromUserId
|
||||
import im.vector.riotx.features.home.room.detail.composer.TextComposerActions
|
||||
import im.vector.riotx.features.home.room.detail.composer.TextComposerAction
|
||||
import im.vector.riotx.features.home.room.detail.composer.TextComposerView
|
||||
import im.vector.riotx.features.home.room.detail.composer.TextComposerViewModel
|
||||
import im.vector.riotx.features.home.room.detail.composer.TextComposerViewState
|
||||
import im.vector.riotx.features.home.room.detail.readreceipts.DisplayReadReceiptsBottomSheet
|
||||
import im.vector.riotx.features.home.room.detail.timeline.TimelineEventController
|
||||
import im.vector.riotx.features.home.room.detail.timeline.action.MessageActionsBottomSheet
|
||||
import im.vector.riotx.features.home.room.detail.timeline.action.MessageActionsDispatcher
|
||||
import im.vector.riotx.features.home.room.detail.timeline.action.SimpleAction
|
||||
import im.vector.riotx.features.home.room.detail.timeline.action.MessageSharedActionViewModel
|
||||
import im.vector.riotx.features.home.room.detail.timeline.action.EventSharedAction
|
||||
import im.vector.riotx.features.home.room.detail.timeline.edithistory.ViewEditHistoryBottomSheet
|
||||
import im.vector.riotx.features.home.room.detail.timeline.item.*
|
||||
import im.vector.riotx.features.home.room.detail.timeline.reactions.ViewReactionsBottomSheet
|
||||
|
@ -193,7 +192,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
|
||||
override fun getMenuRes() = R.menu.menu_timeline
|
||||
|
||||
private lateinit var messageActionsDispatcher: MessageActionsDispatcher
|
||||
private lateinit var sharedActionViewModel: MessageSharedActionViewModel
|
||||
private lateinit var layoutManager: LinearLayoutManager
|
||||
private lateinit var attachmentsHelper: AttachmentsHelper
|
||||
private lateinit var keyboardStateUtils: KeyboardStateUtils
|
||||
|
@ -206,7 +205,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
messageActionsDispatcher = ViewModelProviders.of(requireActivity()).get(MessageActionsDispatcher::class.java)
|
||||
sharedActionViewModel = activityViewModelProvider.get(MessageSharedActionViewModel::class.java)
|
||||
attachmentsHelper = AttachmentsHelper.create(this, this).register()
|
||||
keyboardStateUtils = KeyboardStateUtils(requireActivity())
|
||||
setupToolbar(roomToolbar)
|
||||
|
@ -225,7 +224,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
val message = requireContext().getString(pair.first, *pair.second.toTypedArray())
|
||||
showSnackWithMessage(message, Snackbar.LENGTH_LONG)
|
||||
}
|
||||
messageActionsDispatcher
|
||||
sharedActionViewModel
|
||||
.observe()
|
||||
.subscribe {
|
||||
handleActions(it)
|
||||
|
@ -278,8 +277,8 @@ class RoomDetailFragment @Inject constructor(
|
|||
|
||||
if (savedInstanceState == null) {
|
||||
when (val sharedData = roomDetailArgs.sharedData) {
|
||||
is SharedData.Text -> roomDetailViewModel.process(RoomDetailActions.SendMessage(sharedData.text, false))
|
||||
is SharedData.Attachments -> roomDetailViewModel.process(RoomDetailActions.SendMedia(sharedData.attachmentData))
|
||||
is SharedData.Text -> roomDetailViewModel.handle(RoomDetailAction.SendMessage(sharedData.text, false))
|
||||
is SharedData.Attachments -> roomDetailViewModel.handle(RoomDetailAction.SendMedia(sharedData.attachmentData))
|
||||
null -> Timber.v("No share data to process")
|
||||
}
|
||||
}
|
||||
|
@ -323,7 +322,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
private fun setupNotificationView() {
|
||||
notificationAreaView.delegate = object : NotificationAreaView.Delegate {
|
||||
override fun onTombstoneEventClicked(tombstoneEvent: Event) {
|
||||
roomDetailViewModel.process(RoomDetailActions.HandleTombstoneEvent(tombstoneEvent))
|
||||
roomDetailViewModel.handle(RoomDetailAction.HandleTombstoneEvent(tombstoneEvent))
|
||||
}
|
||||
|
||||
override fun resendUnsentEvents() {
|
||||
|
@ -355,11 +354,11 @@ class RoomDetailFragment @Inject constructor(
|
|||
// This a temporary option during dev as it is not super stable
|
||||
// Cancel all pending actions in room queue and post a dummy
|
||||
// Then mark all sending events as undelivered
|
||||
roomDetailViewModel.process(RoomDetailActions.ClearSendQueue)
|
||||
roomDetailViewModel.handle(RoomDetailAction.ClearSendQueue)
|
||||
return true
|
||||
}
|
||||
if (item.itemId == R.id.resend_all) {
|
||||
roomDetailViewModel.process(RoomDetailActions.ResendAll)
|
||||
roomDetailViewModel.handle(RoomDetailAction.ResendAll)
|
||||
return true
|
||||
}
|
||||
return super.onOptionsItemSelected(item)
|
||||
|
@ -427,7 +426,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
|
||||
notificationDrawerManager.setCurrentRoom(null)
|
||||
|
||||
roomDetailViewModel.process(RoomDetailActions.SaveDraft(composerLayout.composerEditText.text.toString()))
|
||||
roomDetailViewModel.handle(RoomDetailAction.SaveDraft(composerLayout.composerEditText.text.toString()))
|
||||
}
|
||||
|
||||
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
|
||||
|
@ -440,7 +439,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
val reaction = data.getStringExtra(EmojiReactionPickerActivity.EXTRA_REACTION_RESULT)
|
||||
?: return
|
||||
// TODO check if already reacted with that?
|
||||
roomDetailViewModel.process(RoomDetailActions.SendReaction(eventId, reaction))
|
||||
roomDetailViewModel.handle(RoomDetailAction.SendReaction(eventId, reaction))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -498,7 +497,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
override fun performQuickReplyOnHolder(model: EpoxyModel<*>) {
|
||||
(model as? AbsMessageItem)?.attributes?.informationData?.let {
|
||||
val eventId = it.eventId
|
||||
roomDetailViewModel.process(RoomDetailActions.EnterReplyMode(eventId, composerLayout.composerEditText.text.toString()))
|
||||
roomDetailViewModel.handle(RoomDetailAction.EnterReplyMode(eventId, composerLayout.composerEditText.text.toString()))
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -601,11 +600,11 @@ class RoomDetailFragment @Inject constructor(
|
|||
val textMessage = composerLayout.composerEditText.text.toString()
|
||||
if (textMessage.isNotBlank()) {
|
||||
lockSendButton = true
|
||||
roomDetailViewModel.process(RoomDetailActions.SendMessage(textMessage, vectorPreferences.isMarkdownEnabled()))
|
||||
roomDetailViewModel.handle(RoomDetailAction.SendMessage(textMessage, vectorPreferences.isMarkdownEnabled()))
|
||||
}
|
||||
}
|
||||
composerLayout.composerRelatedMessageCloseButton.setOnClickListener {
|
||||
roomDetailViewModel.process(RoomDetailActions.ExitSpecialMode(composerLayout.composerEditText.text.toString()))
|
||||
roomDetailViewModel.handle(RoomDetailAction.ExitSpecialMode(composerLayout.composerEditText.text.toString()))
|
||||
}
|
||||
composerLayout.callback = object : TextComposerView.Callback {
|
||||
override fun onRichContentSelected(contentUri: Uri): Boolean {
|
||||
|
@ -749,7 +748,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
.show()
|
||||
}
|
||||
|
||||
private fun promptReasonToReportContent(action: SimpleAction.ReportContentCustom) {
|
||||
private fun promptReasonToReportContent(action: EventSharedAction.ReportContentCustom) {
|
||||
val inflater = requireActivity().layoutInflater
|
||||
val layout = inflater.inflate(R.layout.dialog_report_content, null)
|
||||
|
||||
|
@ -760,13 +759,13 @@ class RoomDetailFragment @Inject constructor(
|
|||
.setView(layout)
|
||||
.setPositiveButton(R.string.report_content_custom_submit) { _, _ ->
|
||||
val reason = input.text.toString()
|
||||
roomDetailViewModel.process(RoomDetailActions.ReportContent(action.eventId, action.senderId, reason))
|
||||
roomDetailViewModel.handle(RoomDetailAction.ReportContent(action.eventId, action.senderId, reason))
|
||||
}
|
||||
.setNegativeButton(R.string.cancel, null)
|
||||
.show()
|
||||
}
|
||||
|
||||
private fun displayRoomDetailActionResult(result: Async<RoomDetailActions>) {
|
||||
private fun displayRoomDetailActionResult(result: Async<RoomDetailAction>) {
|
||||
when (result) {
|
||||
is Fail -> {
|
||||
AlertDialog.Builder(requireActivity())
|
||||
|
@ -777,7 +776,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
}
|
||||
is Success -> {
|
||||
when (val data = result.invoke()) {
|
||||
is RoomDetailActions.ReportContent -> {
|
||||
is RoomDetailAction.ReportContent -> {
|
||||
when {
|
||||
data.spam -> {
|
||||
AlertDialog.Builder(requireActivity())
|
||||
|
@ -785,7 +784,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
.setMessage(R.string.content_reported_as_spam_content)
|
||||
.setPositiveButton(R.string.ok, null)
|
||||
.setNegativeButton(R.string.block_user) { _, _ ->
|
||||
roomDetailViewModel.process(RoomDetailActions.IgnoreUser(data.senderId))
|
||||
roomDetailViewModel.handle(RoomDetailAction.IgnoreUser(data.senderId))
|
||||
}
|
||||
.show()
|
||||
.withColoredButton(DialogInterface.BUTTON_NEGATIVE)
|
||||
|
@ -796,7 +795,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
.setMessage(R.string.content_reported_as_inappropriate_content)
|
||||
.setPositiveButton(R.string.ok, null)
|
||||
.setNegativeButton(R.string.block_user) { _, _ ->
|
||||
roomDetailViewModel.process(RoomDetailActions.IgnoreUser(data.senderId))
|
||||
roomDetailViewModel.handle(RoomDetailAction.IgnoreUser(data.senderId))
|
||||
}
|
||||
.show()
|
||||
.withColoredButton(DialogInterface.BUTTON_NEGATIVE)
|
||||
|
@ -807,7 +806,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
.setMessage(R.string.content_reported_content)
|
||||
.setPositiveButton(R.string.ok, null)
|
||||
.setNegativeButton(R.string.block_user) { _, _ ->
|
||||
roomDetailViewModel.process(RoomDetailActions.IgnoreUser(data.senderId))
|
||||
roomDetailViewModel.handle(RoomDetailAction.IgnoreUser(data.senderId))
|
||||
}
|
||||
.show()
|
||||
.withColoredButton(DialogInterface.BUTTON_NEGATIVE)
|
||||
|
@ -831,7 +830,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
showSnackWithMessage(getString(R.string.navigate_to_room_when_already_in_the_room))
|
||||
} else {
|
||||
// Highlight and scroll to this event
|
||||
roomDetailViewModel.process(RoomDetailActions.NavigateToEvent(eventId, true))
|
||||
roomDetailViewModel.handle(RoomDetailAction.NavigateToEvent(eventId, true))
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
@ -859,11 +858,11 @@ class RoomDetailFragment @Inject constructor(
|
|||
}
|
||||
|
||||
override fun onEventVisible(event: TimelineEvent) {
|
||||
roomDetailViewModel.process(RoomDetailActions.TimelineEventTurnsVisible(event))
|
||||
roomDetailViewModel.handle(RoomDetailAction.TimelineEventTurnsVisible(event))
|
||||
}
|
||||
|
||||
override fun onEventInvisible(event: TimelineEvent) {
|
||||
roomDetailViewModel.process(RoomDetailActions.TimelineEventTurnsInvisible(event))
|
||||
roomDetailViewModel.handle(RoomDetailAction.TimelineEventTurnsInvisible(event))
|
||||
}
|
||||
|
||||
override fun onEncryptedMessageClicked(informationData: MessageInformationData, view: View) {
|
||||
|
@ -899,10 +898,10 @@ class RoomDetailFragment @Inject constructor(
|
|||
}
|
||||
|
||||
override fun onFileMessageClicked(eventId: String, messageFileContent: MessageFileContent) {
|
||||
val action = RoomDetailActions.DownloadFile(eventId, messageFileContent)
|
||||
val action = RoomDetailAction.DownloadFile(eventId, messageFileContent)
|
||||
// We need WRITE_EXTERNAL permission
|
||||
if (checkPermissions(PERMISSIONS_FOR_WRITING_FILES, this, PERMISSION_REQUEST_CODE_DOWNLOAD_FILE)) {
|
||||
roomDetailViewModel.process(action)
|
||||
roomDetailViewModel.handle(action)
|
||||
} else {
|
||||
roomDetailViewModel.pendingAction = action
|
||||
}
|
||||
|
@ -915,7 +914,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
val action = roomDetailViewModel.pendingAction
|
||||
if (action != null) {
|
||||
roomDetailViewModel.pendingAction = null
|
||||
roomDetailViewModel.process(action)
|
||||
roomDetailViewModel.handle(action)
|
||||
}
|
||||
}
|
||||
PERMISSION_REQUEST_CODE_INCOMING_URI -> {
|
||||
|
@ -946,7 +945,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
}
|
||||
|
||||
override fun onLoadMore(direction: Timeline.Direction) {
|
||||
roomDetailViewModel.process(RoomDetailActions.LoadMoreTimelineEvents(direction))
|
||||
roomDetailViewModel.handle(RoomDetailAction.LoadMoreTimelineEvents(direction))
|
||||
}
|
||||
|
||||
override fun onEventCellClicked(informationData: MessageInformationData, messageContent: MessageContent?, view: View) {
|
||||
|
@ -976,10 +975,10 @@ class RoomDetailFragment @Inject constructor(
|
|||
override fun onClickOnReactionPill(informationData: MessageInformationData, reaction: String, on: Boolean) {
|
||||
if (on) {
|
||||
// we should test the current real state of reaction on this event
|
||||
roomDetailViewModel.process(RoomDetailActions.SendReaction(informationData.eventId, reaction))
|
||||
roomDetailViewModel.handle(RoomDetailAction.SendReaction(informationData.eventId, reaction))
|
||||
} else {
|
||||
// I need to redact a reaction
|
||||
roomDetailViewModel.process(RoomDetailActions.UndoReaction(informationData.eventId, reaction))
|
||||
roomDetailViewModel.handle(RoomDetailAction.UndoReaction(informationData.eventId, reaction))
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1027,35 +1026,35 @@ class RoomDetailFragment @Inject constructor(
|
|||
}
|
||||
}
|
||||
if (nextReadMarkerId != null) {
|
||||
roomDetailViewModel.process(RoomDetailActions.SetReadMarkerAction(nextReadMarkerId))
|
||||
roomDetailViewModel.handle(RoomDetailAction.SetReadMarkerAction(nextReadMarkerId))
|
||||
}
|
||||
}
|
||||
|
||||
// AutocompleteUserPresenter.Callback
|
||||
|
||||
override fun onQueryUsers(query: CharSequence?) {
|
||||
textComposerViewModel.process(TextComposerActions.QueryUsers(query))
|
||||
textComposerViewModel.handle(TextComposerAction.QueryUsers(query))
|
||||
}
|
||||
|
||||
private fun handleActions(action: SimpleAction) {
|
||||
private fun handleActions(action: EventSharedAction) {
|
||||
when (action) {
|
||||
is SimpleAction.AddReaction -> {
|
||||
is EventSharedAction.AddReaction -> {
|
||||
startActivityForResult(EmojiReactionPickerActivity.intent(requireContext(), action.eventId), REACTION_SELECT_REQUEST_CODE)
|
||||
}
|
||||
is SimpleAction.ViewReactions -> {
|
||||
is EventSharedAction.ViewReactions -> {
|
||||
ViewReactionsBottomSheet.newInstance(roomDetailArgs.roomId, action.messageInformationData)
|
||||
.show(requireActivity().supportFragmentManager, "DISPLAY_REACTIONS")
|
||||
}
|
||||
is SimpleAction.Copy -> {
|
||||
is EventSharedAction.Copy -> {
|
||||
// I need info about the current selected message :/
|
||||
copyToClipboard(requireContext(), action.content, false)
|
||||
val msg = requireContext().getString(R.string.copied_to_clipboard)
|
||||
showSnackWithMessage(msg, Snackbar.LENGTH_SHORT)
|
||||
}
|
||||
is SimpleAction.Delete -> {
|
||||
roomDetailViewModel.process(RoomDetailActions.RedactAction(action.eventId, context?.getString(R.string.event_redacted_by_user_reason)))
|
||||
is EventSharedAction.Delete -> {
|
||||
roomDetailViewModel.handle(RoomDetailAction.RedactAction(action.eventId, context?.getString(R.string.event_redacted_by_user_reason)))
|
||||
}
|
||||
is SimpleAction.Share -> {
|
||||
is EventSharedAction.Share -> {
|
||||
// TODO current data communication is too limited
|
||||
// Need to now the media type
|
||||
// TODO bad, just POC
|
||||
|
@ -1083,10 +1082,10 @@ class RoomDetailFragment @Inject constructor(
|
|||
}
|
||||
)
|
||||
}
|
||||
is SimpleAction.ViewEditHistory -> {
|
||||
is EventSharedAction.ViewEditHistory -> {
|
||||
onEditedDecorationClicked(action.messageInformationData)
|
||||
}
|
||||
is SimpleAction.ViewSource -> {
|
||||
is EventSharedAction.ViewSource -> {
|
||||
val view = LayoutInflater.from(requireContext()).inflate(R.layout.dialog_event_content, null)
|
||||
view.findViewById<TextView>(R.id.event_content_text_view)?.let {
|
||||
it.text = action.content
|
||||
|
@ -1097,7 +1096,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
.setPositiveButton(R.string.ok, null)
|
||||
.show()
|
||||
}
|
||||
is SimpleAction.ViewDecryptedSource -> {
|
||||
is EventSharedAction.ViewDecryptedSource -> {
|
||||
val view = LayoutInflater.from(requireContext()).inflate(R.layout.dialog_event_content, null)
|
||||
view.findViewById<TextView>(R.id.event_content_text_view)?.let {
|
||||
it.text = action.content
|
||||
|
@ -1108,42 +1107,42 @@ class RoomDetailFragment @Inject constructor(
|
|||
.setPositiveButton(R.string.ok, null)
|
||||
.show()
|
||||
}
|
||||
is SimpleAction.QuickReact -> {
|
||||
is EventSharedAction.QuickReact -> {
|
||||
// eventId,ClickedOn,Add
|
||||
roomDetailViewModel.process(RoomDetailActions.UpdateQuickReactAction(action.eventId, action.clickedOn, action.add))
|
||||
roomDetailViewModel.handle(RoomDetailAction.UpdateQuickReactAction(action.eventId, action.clickedOn, action.add))
|
||||
}
|
||||
is SimpleAction.Edit -> {
|
||||
roomDetailViewModel.process(RoomDetailActions.EnterEditMode(action.eventId, composerLayout.composerEditText.text.toString()))
|
||||
is EventSharedAction.Edit -> {
|
||||
roomDetailViewModel.handle(RoomDetailAction.EnterEditMode(action.eventId, composerLayout.composerEditText.text.toString()))
|
||||
}
|
||||
is SimpleAction.Quote -> {
|
||||
roomDetailViewModel.process(RoomDetailActions.EnterQuoteMode(action.eventId, composerLayout.composerEditText.text.toString()))
|
||||
is EventSharedAction.Quote -> {
|
||||
roomDetailViewModel.handle(RoomDetailAction.EnterQuoteMode(action.eventId, composerLayout.composerEditText.text.toString()))
|
||||
}
|
||||
is SimpleAction.Reply -> {
|
||||
roomDetailViewModel.process(RoomDetailActions.EnterReplyMode(action.eventId, composerLayout.composerEditText.text.toString()))
|
||||
is EventSharedAction.Reply -> {
|
||||
roomDetailViewModel.handle(RoomDetailAction.EnterReplyMode(action.eventId, composerLayout.composerEditText.text.toString()))
|
||||
}
|
||||
is SimpleAction.CopyPermalink -> {
|
||||
is EventSharedAction.CopyPermalink -> {
|
||||
val permalink = PermalinkFactory.createPermalink(roomDetailArgs.roomId, action.eventId)
|
||||
copyToClipboard(requireContext(), permalink, false)
|
||||
showSnackWithMessage(requireContext().getString(R.string.copied_to_clipboard), Snackbar.LENGTH_SHORT)
|
||||
}
|
||||
is SimpleAction.Resend -> {
|
||||
roomDetailViewModel.process(RoomDetailActions.ResendMessage(action.eventId))
|
||||
is EventSharedAction.Resend -> {
|
||||
roomDetailViewModel.handle(RoomDetailAction.ResendMessage(action.eventId))
|
||||
}
|
||||
is SimpleAction.Remove -> {
|
||||
roomDetailViewModel.process(RoomDetailActions.RemoveFailedEcho(action.eventId))
|
||||
is EventSharedAction.Remove -> {
|
||||
roomDetailViewModel.handle(RoomDetailAction.RemoveFailedEcho(action.eventId))
|
||||
}
|
||||
is SimpleAction.ReportContentSpam -> {
|
||||
roomDetailViewModel.process(RoomDetailActions.ReportContent(
|
||||
is EventSharedAction.ReportContentSpam -> {
|
||||
roomDetailViewModel.handle(RoomDetailAction.ReportContent(
|
||||
action.eventId, action.senderId, "This message is spam", spam = true))
|
||||
}
|
||||
is SimpleAction.ReportContentInappropriate -> {
|
||||
roomDetailViewModel.process(RoomDetailActions.ReportContent(
|
||||
is EventSharedAction.ReportContentInappropriate -> {
|
||||
roomDetailViewModel.handle(RoomDetailAction.ReportContent(
|
||||
action.eventId, action.senderId, "This message is inappropriate", inappropriate = true))
|
||||
}
|
||||
is SimpleAction.ReportContentCustom -> {
|
||||
is EventSharedAction.ReportContentCustom -> {
|
||||
promptReasonToReportContent(action)
|
||||
}
|
||||
else -> {
|
||||
else -> {
|
||||
Toast.makeText(context, "Action $action is not implemented yet", Toast.LENGTH_LONG).show()
|
||||
}
|
||||
}
|
||||
|
@ -1210,22 +1209,22 @@ class RoomDetailFragment @Inject constructor(
|
|||
|
||||
override fun onAcceptInvite() {
|
||||
notificationDrawerManager.clearMemberShipNotificationForRoom(roomDetailArgs.roomId)
|
||||
roomDetailViewModel.process(RoomDetailActions.AcceptInvite)
|
||||
roomDetailViewModel.handle(RoomDetailAction.AcceptInvite)
|
||||
}
|
||||
|
||||
override fun onRejectInvite() {
|
||||
notificationDrawerManager.clearMemberShipNotificationForRoom(roomDetailArgs.roomId)
|
||||
roomDetailViewModel.process(RoomDetailActions.RejectInvite)
|
||||
roomDetailViewModel.handle(RoomDetailAction.RejectInvite)
|
||||
}
|
||||
|
||||
// JumpToReadMarkerView.Callback
|
||||
|
||||
override fun onJumpToReadMarkerClicked(readMarkerId: String) {
|
||||
roomDetailViewModel.process(RoomDetailActions.NavigateToEvent(readMarkerId, false))
|
||||
roomDetailViewModel.handle(RoomDetailAction.NavigateToEvent(readMarkerId, false))
|
||||
}
|
||||
|
||||
override fun onClearReadMarkerClicked() {
|
||||
roomDetailViewModel.process(RoomDetailActions.MarkAllAsRead)
|
||||
roomDetailViewModel.handle(RoomDetailAction.MarkAllAsRead)
|
||||
}
|
||||
|
||||
// AttachmentTypeSelectorView.Callback
|
||||
|
@ -1252,7 +1251,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
// AttachmentsHelper.Callback
|
||||
|
||||
override fun onContentAttachmentsReady(attachments: List<ContentAttachmentData>) {
|
||||
roomDetailViewModel.process(RoomDetailActions.SendMedia(attachments))
|
||||
roomDetailViewModel.handle(RoomDetailAction.SendMedia(attachments))
|
||||
}
|
||||
|
||||
override fun onAttachmentsProcessFailed() {
|
||||
|
@ -1262,6 +1261,6 @@ class RoomDetailFragment @Inject constructor(
|
|||
override fun onContactAttachmentReady(contactAttachment: ContactAttachment) {
|
||||
super.onContactAttachmentReady(contactAttachment)
|
||||
val formattedContact = contactAttachment.toHumanReadable()
|
||||
roomDetailViewModel.process(RoomDetailActions.SendMessage(formattedContact, false))
|
||||
roomDetailViewModel.handle(RoomDetailAction.SendMessage(formattedContact, false))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -69,12 +69,12 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
private val vectorPreferences: VectorPreferences,
|
||||
private val stringProvider: StringProvider,
|
||||
private val session: Session
|
||||
) : VectorViewModel<RoomDetailViewState>(initialState) {
|
||||
) : VectorViewModel<RoomDetailViewState, RoomDetailAction>(initialState) {
|
||||
|
||||
private val room = session.getRoom(initialState.roomId)!!
|
||||
private val eventId = initialState.eventId
|
||||
private val invisibleEventsObservable = BehaviorRelay.create<RoomDetailActions.TimelineEventTurnsInvisible>()
|
||||
private val visibleEventsObservable = BehaviorRelay.create<RoomDetailActions.TimelineEventTurnsVisible>()
|
||||
private val invisibleEventsObservable = BehaviorRelay.create<RoomDetailAction.TimelineEventTurnsInvisible>()
|
||||
private val visibleEventsObservable = BehaviorRelay.create<RoomDetailAction.TimelineEventTurnsVisible>()
|
||||
private val timelineSettings = if (userPreferencesProvider.shouldShowHiddenEvents()) {
|
||||
TimelineSettings(30,
|
||||
filterEdits = false,
|
||||
|
@ -92,12 +92,12 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
private var timeline = room.createTimeline(eventId, timelineSettings)
|
||||
|
||||
// Can be used for several actions, for a one shot result
|
||||
private val _requestLiveData = MutableLiveData<LiveEvent<Async<RoomDetailActions>>>()
|
||||
val requestLiveData: LiveData<LiveEvent<Async<RoomDetailActions>>>
|
||||
private val _requestLiveData = MutableLiveData<LiveEvent<Async<RoomDetailAction>>>()
|
||||
val requestLiveData: LiveData<LiveEvent<Async<RoomDetailAction>>>
|
||||
get() = _requestLiveData
|
||||
|
||||
// Slot to keep a pending action during permission request
|
||||
var pendingAction: RoomDetailActions? = null
|
||||
var pendingAction: RoomDetailAction? = null
|
||||
// Slot to keep a pending uri during permission request
|
||||
var pendingUri: Uri? = null
|
||||
|
||||
|
@ -129,46 +129,46 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
setState { copy(timeline = this@RoomDetailViewModel.timeline) }
|
||||
}
|
||||
|
||||
fun process(action: RoomDetailActions) {
|
||||
override fun handle(action: RoomDetailAction) {
|
||||
when (action) {
|
||||
is RoomDetailActions.SaveDraft -> handleSaveDraft(action)
|
||||
is RoomDetailActions.SendMessage -> handleSendMessage(action)
|
||||
is RoomDetailActions.SendMedia -> handleSendMedia(action)
|
||||
is RoomDetailActions.TimelineEventTurnsVisible -> handleEventVisible(action)
|
||||
is RoomDetailActions.TimelineEventTurnsInvisible -> handleEventInvisible(action)
|
||||
is RoomDetailActions.LoadMoreTimelineEvents -> handleLoadMore(action)
|
||||
is RoomDetailActions.SendReaction -> handleSendReaction(action)
|
||||
is RoomDetailActions.AcceptInvite -> handleAcceptInvite()
|
||||
is RoomDetailActions.RejectInvite -> handleRejectInvite()
|
||||
is RoomDetailActions.RedactAction -> handleRedactEvent(action)
|
||||
is RoomDetailActions.UndoReaction -> handleUndoReact(action)
|
||||
is RoomDetailActions.UpdateQuickReactAction -> handleUpdateQuickReaction(action)
|
||||
is RoomDetailActions.ExitSpecialMode -> handleExitSpecialMode(action)
|
||||
is RoomDetailActions.EnterEditMode -> handleEditAction(action)
|
||||
is RoomDetailActions.EnterQuoteMode -> handleQuoteAction(action)
|
||||
is RoomDetailActions.EnterReplyMode -> handleReplyAction(action)
|
||||
is RoomDetailActions.DownloadFile -> handleDownloadFile(action)
|
||||
is RoomDetailActions.NavigateToEvent -> handleNavigateToEvent(action)
|
||||
is RoomDetailActions.HandleTombstoneEvent -> handleTombstoneEvent(action)
|
||||
is RoomDetailActions.ResendMessage -> handleResendEvent(action)
|
||||
is RoomDetailActions.RemoveFailedEcho -> handleRemove(action)
|
||||
is RoomDetailActions.ClearSendQueue -> handleClearSendQueue()
|
||||
is RoomDetailActions.ResendAll -> handleResendAll()
|
||||
is RoomDetailActions.SetReadMarkerAction -> handleSetReadMarkerAction(action)
|
||||
is RoomDetailActions.MarkAllAsRead -> handleMarkAllAsRead()
|
||||
is RoomDetailActions.ReportContent -> handleReportContent(action)
|
||||
is RoomDetailActions.IgnoreUser -> handleIgnoreUser(action)
|
||||
is RoomDetailAction.SaveDraft -> handleSaveDraft(action)
|
||||
is RoomDetailAction.SendMessage -> handleSendMessage(action)
|
||||
is RoomDetailAction.SendMedia -> handleSendMedia(action)
|
||||
is RoomDetailAction.TimelineEventTurnsVisible -> handleEventVisible(action)
|
||||
is RoomDetailAction.TimelineEventTurnsInvisible -> handleEventInvisible(action)
|
||||
is RoomDetailAction.LoadMoreTimelineEvents -> handleLoadMore(action)
|
||||
is RoomDetailAction.SendReaction -> handleSendReaction(action)
|
||||
is RoomDetailAction.AcceptInvite -> handleAcceptInvite()
|
||||
is RoomDetailAction.RejectInvite -> handleRejectInvite()
|
||||
is RoomDetailAction.RedactAction -> handleRedactEvent(action)
|
||||
is RoomDetailAction.UndoReaction -> handleUndoReact(action)
|
||||
is RoomDetailAction.UpdateQuickReactAction -> handleUpdateQuickReaction(action)
|
||||
is RoomDetailAction.ExitSpecialMode -> handleExitSpecialMode(action)
|
||||
is RoomDetailAction.EnterEditMode -> handleEditAction(action)
|
||||
is RoomDetailAction.EnterQuoteMode -> handleQuoteAction(action)
|
||||
is RoomDetailAction.EnterReplyMode -> handleReplyAction(action)
|
||||
is RoomDetailAction.DownloadFile -> handleDownloadFile(action)
|
||||
is RoomDetailAction.NavigateToEvent -> handleNavigateToEvent(action)
|
||||
is RoomDetailAction.HandleTombstoneEvent -> handleTombstoneEvent(action)
|
||||
is RoomDetailAction.ResendMessage -> handleResendEvent(action)
|
||||
is RoomDetailAction.RemoveFailedEcho -> handleRemove(action)
|
||||
is RoomDetailAction.ClearSendQueue -> handleClearSendQueue()
|
||||
is RoomDetailAction.ResendAll -> handleResendAll()
|
||||
is RoomDetailAction.SetReadMarkerAction -> handleSetReadMarkerAction(action)
|
||||
is RoomDetailAction.MarkAllAsRead -> handleMarkAllAsRead()
|
||||
is RoomDetailAction.ReportContent -> handleReportContent(action)
|
||||
is RoomDetailAction.IgnoreUser -> handleIgnoreUser(action)
|
||||
}
|
||||
}
|
||||
|
||||
private fun handleEventInvisible(action: RoomDetailActions.TimelineEventTurnsInvisible) {
|
||||
private fun handleEventInvisible(action: RoomDetailAction.TimelineEventTurnsInvisible) {
|
||||
invisibleEventsObservable.accept(action)
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert a send mode to a draft and save the draft
|
||||
*/
|
||||
private fun handleSaveDraft(action: RoomDetailActions.SaveDraft) {
|
||||
private fun handleSaveDraft(action: RoomDetailAction.SaveDraft) {
|
||||
withState {
|
||||
when (it.sendMode) {
|
||||
is SendMode.REGULAR -> room.saveDraft(UserDraft.REGULAR(action.draft))
|
||||
|
@ -211,7 +211,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
.disposeOnClear()
|
||||
}
|
||||
|
||||
private fun handleTombstoneEvent(action: RoomDetailActions.HandleTombstoneEvent) {
|
||||
private fun handleTombstoneEvent(action: RoomDetailAction.HandleTombstoneEvent) {
|
||||
val tombstoneContent = action.event.getClearContent().toModel<RoomTombstoneContent>()
|
||||
?: return
|
||||
|
||||
|
@ -267,7 +267,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
|
||||
// PRIVATE METHODS *****************************************************************************
|
||||
|
||||
private fun handleSendMessage(action: RoomDetailActions.SendMessage) {
|
||||
private fun handleSendMessage(action: RoomDetailAction.SendMessage) {
|
||||
withState { state ->
|
||||
when (state.sendMode) {
|
||||
is SendMode.REGULAR -> {
|
||||
|
@ -458,20 +458,20 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
})
|
||||
}
|
||||
|
||||
private fun handleSendReaction(action: RoomDetailActions.SendReaction) {
|
||||
private fun handleSendReaction(action: RoomDetailAction.SendReaction) {
|
||||
room.sendReaction(action.targetEventId, action.reaction)
|
||||
}
|
||||
|
||||
private fun handleRedactEvent(action: RoomDetailActions.RedactAction) {
|
||||
private fun handleRedactEvent(action: RoomDetailAction.RedactAction) {
|
||||
val event = room.getTimeLineEvent(action.targetEventId) ?: return
|
||||
room.redactEvent(event.root, action.reason)
|
||||
}
|
||||
|
||||
private fun handleUndoReact(action: RoomDetailActions.UndoReaction) {
|
||||
private fun handleUndoReact(action: RoomDetailAction.UndoReaction) {
|
||||
room.undoReaction(action.targetEventId, action.reaction)
|
||||
}
|
||||
|
||||
private fun handleUpdateQuickReaction(action: RoomDetailActions.UpdateQuickReactAction) {
|
||||
private fun handleUpdateQuickReaction(action: RoomDetailAction.UpdateQuickReactAction) {
|
||||
if (action.add) {
|
||||
room.sendReaction(action.targetEventId, action.selectedReaction)
|
||||
} else {
|
||||
|
@ -479,7 +479,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleSendMedia(action: RoomDetailActions.SendMedia) {
|
||||
private fun handleSendMedia(action: RoomDetailAction.SendMedia) {
|
||||
val attachments = action.attachments
|
||||
val homeServerCapabilities = session.getHomeServerCapabilities()
|
||||
val maxUploadFileSize = homeServerCapabilities.maxUploadFileSize
|
||||
|
@ -496,19 +496,19 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleEventVisible(action: RoomDetailActions.TimelineEventTurnsVisible) {
|
||||
private fun handleEventVisible(action: RoomDetailAction.TimelineEventTurnsVisible) {
|
||||
if (action.event.root.sendState.isSent()) { // ignore pending/local events
|
||||
visibleEventsObservable.accept(action)
|
||||
}
|
||||
// We need to update this with the related m.replace also (to move read receipt)
|
||||
action.event.annotations?.editSummary?.sourceEvents?.forEach {
|
||||
room.getTimeLineEvent(it)?.let { event ->
|
||||
visibleEventsObservable.accept(RoomDetailActions.TimelineEventTurnsVisible(event))
|
||||
visibleEventsObservable.accept(RoomDetailAction.TimelineEventTurnsVisible(event))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun handleLoadMore(action: RoomDetailActions.LoadMoreTimelineEvents) {
|
||||
private fun handleLoadMore(action: RoomDetailAction.LoadMoreTimelineEvents) {
|
||||
timeline.paginate(action.direction, PAGINATION_COUNT)
|
||||
}
|
||||
|
||||
|
@ -520,7 +520,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
room.join(callback = object : MatrixCallback<Unit> {})
|
||||
}
|
||||
|
||||
private fun handleEditAction(action: RoomDetailActions.EnterEditMode) {
|
||||
private fun handleEditAction(action: RoomDetailAction.EnterEditMode) {
|
||||
saveCurrentDraft(action.draft)
|
||||
|
||||
room.getTimeLineEvent(action.eventId)?.let { timelineEvent ->
|
||||
|
@ -530,7 +530,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleQuoteAction(action: RoomDetailActions.EnterQuoteMode) {
|
||||
private fun handleQuoteAction(action: RoomDetailAction.EnterQuoteMode) {
|
||||
saveCurrentDraft(action.draft)
|
||||
|
||||
room.getTimeLineEvent(action.eventId)?.let { timelineEvent ->
|
||||
|
@ -547,7 +547,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleReplyAction(action: RoomDetailActions.EnterReplyMode) {
|
||||
private fun handleReplyAction(action: RoomDetailAction.EnterReplyMode) {
|
||||
saveCurrentDraft(action.draft)
|
||||
|
||||
room.getTimeLineEvent(action.eventId)?.let { timelineEvent ->
|
||||
|
@ -578,7 +578,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleExitSpecialMode(action: RoomDetailActions.ExitSpecialMode) {
|
||||
private fun handleExitSpecialMode(action: RoomDetailAction.ExitSpecialMode) {
|
||||
withState { state ->
|
||||
// For edit, just delete the current draft
|
||||
if (state.sendMode is SendMode.EDIT) {
|
||||
|
@ -590,7 +590,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleDownloadFile(action: RoomDetailActions.DownloadFile) {
|
||||
private fun handleDownloadFile(action: RoomDetailAction.DownloadFile) {
|
||||
session.downloadFile(
|
||||
FileService.DownloadMode.TO_EXPORT,
|
||||
action.eventId,
|
||||
|
@ -616,7 +616,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
})
|
||||
}
|
||||
|
||||
private fun handleNavigateToEvent(action: RoomDetailActions.NavigateToEvent) {
|
||||
private fun handleNavigateToEvent(action: RoomDetailAction.NavigateToEvent) {
|
||||
val targetEventId: String = action.eventId
|
||||
val correctedEventId = timeline.getFirstDisplayableEventId(targetEventId) ?: targetEventId
|
||||
val indexOfEvent = timeline.getIndexOfEvent(correctedEventId)
|
||||
|
@ -630,7 +630,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
_navigateToEvent.postLiveEvent(correctedEventId)
|
||||
}
|
||||
|
||||
private fun handleResendEvent(action: RoomDetailActions.ResendMessage) {
|
||||
private fun handleResendEvent(action: RoomDetailAction.ResendMessage) {
|
||||
val targetEventId = action.eventId
|
||||
room.getTimeLineEvent(targetEventId)?.let {
|
||||
// State must be UNDELIVERED or Failed
|
||||
|
@ -648,7 +648,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleRemove(action: RoomDetailActions.RemoveFailedEcho) {
|
||||
private fun handleRemove(action: RoomDetailAction.RemoveFailedEcho) {
|
||||
val targetEventId = action.eventId
|
||||
room.getTimeLineEvent(targetEventId)?.let {
|
||||
// State must be UNDELIVERED or Failed
|
||||
|
@ -683,7 +683,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
.disposeOnClear()
|
||||
}
|
||||
|
||||
private fun handleSetReadMarkerAction(action: RoomDetailActions.SetReadMarkerAction) = withState {
|
||||
private fun handleSetReadMarkerAction(action: RoomDetailAction.SetReadMarkerAction) = withState {
|
||||
var readMarkerId = action.eventId
|
||||
val indexOfEvent = timeline.getIndexOfEvent(readMarkerId)
|
||||
// force to set the read marker on the next event
|
||||
|
@ -699,7 +699,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
room.markAllAsRead(object : MatrixCallback<Any> {})
|
||||
}
|
||||
|
||||
private fun handleReportContent(action: RoomDetailActions.ReportContent) {
|
||||
private fun handleReportContent(action: RoomDetailAction.ReportContent) {
|
||||
room.reportContent(action.eventId, -100, action.reason, object : MatrixCallback<Unit> {
|
||||
override fun onSuccess(data: Unit) {
|
||||
_requestLiveData.postValue(LiveEvent(Success(action)))
|
||||
|
@ -711,7 +711,7 @@ class RoomDetailViewModel @AssistedInject constructor(@Assisted initialState: Ro
|
|||
})
|
||||
}
|
||||
|
||||
private fun handleIgnoreUser(action: RoomDetailActions.IgnoreUser) {
|
||||
private fun handleIgnoreUser(action: RoomDetailAction.IgnoreUser) {
|
||||
if (action.userId.isNullOrEmpty()) {
|
||||
return
|
||||
}
|
||||
|
|
|
@ -16,6 +16,8 @@
|
|||
|
||||
package im.vector.riotx.features.home.room.detail.composer
|
||||
|
||||
sealed class TextComposerActions {
|
||||
data class QueryUsers(val query: CharSequence?) : TextComposerActions()
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class TextComposerAction : VectorViewModelAction {
|
||||
data class QueryUsers(val query: CharSequence?) : TextComposerAction()
|
||||
}
|
|
@ -36,7 +36,7 @@ typealias AutocompleteUserQuery = CharSequence
|
|||
|
||||
class TextComposerViewModel @AssistedInject constructor(@Assisted initialState: TextComposerViewState,
|
||||
private val session: Session
|
||||
) : VectorViewModel<TextComposerViewState>(initialState) {
|
||||
) : VectorViewModel<TextComposerViewState, TextComposerAction>(initialState) {
|
||||
|
||||
private val room = session.getRoom(initialState.roomId)!!
|
||||
private val roomId = initialState.roomId
|
||||
|
@ -52,7 +52,7 @@ class TextComposerViewModel @AssistedInject constructor(@Assisted initialState:
|
|||
|
||||
@JvmStatic
|
||||
override fun create(viewModelContext: ViewModelContext, state: TextComposerViewState): TextComposerViewModel? {
|
||||
val fragment : RoomDetailFragment = (viewModelContext as FragmentViewModelContext).fragment()
|
||||
val fragment: RoomDetailFragment = (viewModelContext as FragmentViewModelContext).fragment()
|
||||
return fragment.textComposerViewModelFactory.create(state)
|
||||
}
|
||||
}
|
||||
|
@ -61,13 +61,13 @@ class TextComposerViewModel @AssistedInject constructor(@Assisted initialState:
|
|||
observeUsersQuery()
|
||||
}
|
||||
|
||||
fun process(action: TextComposerActions) {
|
||||
override fun handle(action: TextComposerAction) {
|
||||
when (action) {
|
||||
is TextComposerActions.QueryUsers -> handleQueryUsers(action)
|
||||
is TextComposerAction.QueryUsers -> handleQueryUsers(action)
|
||||
}
|
||||
}
|
||||
|
||||
private fun handleQueryUsers(action: TextComposerActions.QueryUsers) {
|
||||
private fun handleQueryUsers(action: TextComposerAction.QueryUsers) {
|
||||
val query = Option.fromNullable(action.query)
|
||||
usersQueryObservable.accept(query)
|
||||
}
|
||||
|
@ -84,8 +84,7 @@ class TextComposerViewModel @AssistedInject constructor(@Assisted initialState:
|
|||
users
|
||||
} else {
|
||||
users.filter {
|
||||
it.displayName?.startsWith(prefix = filter, ignoreCase = true)
|
||||
?: false
|
||||
it.displayName?.startsWith(prefix = filter, ignoreCase = true) ?: false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -19,66 +19,67 @@ package im.vector.riotx.features.home.room.detail.timeline.action
|
|||
import androidx.annotation.DrawableRes
|
||||
import androidx.annotation.StringRes
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.platform.VectorSharedAction
|
||||
import im.vector.riotx.features.home.room.detail.timeline.item.MessageInformationData
|
||||
|
||||
sealed class SimpleAction(@StringRes val titleRes: Int, @DrawableRes val iconResId: Int) {
|
||||
sealed class EventSharedAction(@StringRes val titleRes: Int, @DrawableRes val iconResId: Int) : VectorSharedAction {
|
||||
data class AddReaction(val eventId: String) :
|
||||
SimpleAction(R.string.message_add_reaction, R.drawable.ic_add_reaction)
|
||||
EventSharedAction(R.string.message_add_reaction, R.drawable.ic_add_reaction)
|
||||
|
||||
data class Copy(val content: String) :
|
||||
SimpleAction(R.string.copy, R.drawable.ic_copy)
|
||||
EventSharedAction(R.string.copy, R.drawable.ic_copy)
|
||||
|
||||
data class Edit(val eventId: String) :
|
||||
SimpleAction(R.string.edit, R.drawable.ic_edit)
|
||||
EventSharedAction(R.string.edit, R.drawable.ic_edit)
|
||||
|
||||
data class Quote(val eventId: String) :
|
||||
SimpleAction(R.string.quote, R.drawable.ic_quote)
|
||||
EventSharedAction(R.string.quote, R.drawable.ic_quote)
|
||||
|
||||
data class Reply(val eventId: String) :
|
||||
SimpleAction(R.string.reply, R.drawable.ic_reply)
|
||||
EventSharedAction(R.string.reply, R.drawable.ic_reply)
|
||||
|
||||
data class Share(val imageUrl: String) :
|
||||
SimpleAction(R.string.share, R.drawable.ic_share)
|
||||
EventSharedAction(R.string.share, R.drawable.ic_share)
|
||||
|
||||
data class Resend(val eventId: String) :
|
||||
SimpleAction(R.string.global_retry, R.drawable.ic_refresh_cw)
|
||||
EventSharedAction(R.string.global_retry, R.drawable.ic_refresh_cw)
|
||||
|
||||
data class Remove(val eventId: String) :
|
||||
SimpleAction(R.string.remove, R.drawable.ic_trash)
|
||||
EventSharedAction(R.string.remove, R.drawable.ic_trash)
|
||||
|
||||
data class Delete(val eventId: String) :
|
||||
SimpleAction(R.string.delete, R.drawable.ic_delete)
|
||||
EventSharedAction(R.string.delete, R.drawable.ic_delete)
|
||||
|
||||
data class Cancel(val eventId: String) :
|
||||
SimpleAction(R.string.cancel, R.drawable.ic_close_round)
|
||||
EventSharedAction(R.string.cancel, R.drawable.ic_close_round)
|
||||
|
||||
data class ViewSource(val content: String) :
|
||||
SimpleAction(R.string.view_source, R.drawable.ic_view_source)
|
||||
EventSharedAction(R.string.view_source, R.drawable.ic_view_source)
|
||||
|
||||
data class ViewDecryptedSource(val content: String) :
|
||||
SimpleAction(R.string.view_decrypted_source, R.drawable.ic_view_source)
|
||||
EventSharedAction(R.string.view_decrypted_source, R.drawable.ic_view_source)
|
||||
|
||||
data class CopyPermalink(val eventId: String) :
|
||||
SimpleAction(R.string.permalink, R.drawable.ic_permalink)
|
||||
EventSharedAction(R.string.permalink, R.drawable.ic_permalink)
|
||||
|
||||
data class ReportContent(val eventId: String, val senderId: String?) :
|
||||
SimpleAction(R.string.report_content, R.drawable.ic_flag)
|
||||
EventSharedAction(R.string.report_content, R.drawable.ic_flag)
|
||||
|
||||
data class ReportContentSpam(val eventId: String, val senderId: String?) :
|
||||
SimpleAction(R.string.report_content_spam, R.drawable.ic_report_spam)
|
||||
EventSharedAction(R.string.report_content_spam, R.drawable.ic_report_spam)
|
||||
|
||||
data class ReportContentInappropriate(val eventId: String, val senderId: String?) :
|
||||
SimpleAction(R.string.report_content_inappropriate, R.drawable.ic_report_inappropriate)
|
||||
EventSharedAction(R.string.report_content_inappropriate, R.drawable.ic_report_inappropriate)
|
||||
|
||||
data class ReportContentCustom(val eventId: String, val senderId: String?) :
|
||||
SimpleAction(R.string.report_content_custom, R.drawable.ic_report_custom)
|
||||
EventSharedAction(R.string.report_content_custom, R.drawable.ic_report_custom)
|
||||
|
||||
data class QuickReact(val eventId: String, val clickedOn: String, val add: Boolean) :
|
||||
SimpleAction(0, 0)
|
||||
EventSharedAction(0, 0)
|
||||
|
||||
data class ViewReactions(val messageInformationData: MessageInformationData) :
|
||||
SimpleAction(R.string.message_view_reaction, R.drawable.ic_view_reactions)
|
||||
EventSharedAction(R.string.message_view_reaction, R.drawable.ic_view_reactions)
|
||||
|
||||
data class ViewEditHistory(val messageInformationData: MessageInformationData) :
|
||||
SimpleAction(R.string.message_view_edit_history, R.drawable.ic_view_edit_history)
|
||||
EventSharedAction(R.string.message_view_edit_history, R.drawable.ic_view_edit_history)
|
||||
}
|
|
@ -0,0 +1,23 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.home.room.detail.timeline.action
|
||||
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class MessageActionsAction : VectorViewModelAction {
|
||||
object ToggleReportMenu : MessageActionsAction()
|
||||
}
|
|
@ -19,7 +19,6 @@ import android.os.Bundle
|
|||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import butterknife.BindView
|
||||
|
@ -47,7 +46,7 @@ class MessageActionsBottomSheet : VectorBaseBottomSheetDialogFragment(), Message
|
|||
|
||||
override val showExpanded = true
|
||||
|
||||
private lateinit var messageActionsStore: MessageActionsDispatcher
|
||||
private lateinit var sharedActionViewModel: MessageSharedActionViewModel
|
||||
|
||||
override fun injectWith(screenComponent: ScreenComponent) {
|
||||
screenComponent.inject(this)
|
||||
|
@ -61,7 +60,7 @@ class MessageActionsBottomSheet : VectorBaseBottomSheetDialogFragment(), Message
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
messageActionsStore = ViewModelProviders.of(requireActivity()).get(MessageActionsDispatcher::class.java)
|
||||
sharedActionViewModel = activityViewModelProvider.get(MessageSharedActionViewModel::class.java)
|
||||
recyclerView.layoutManager = LinearLayoutManager(requireContext(), RecyclerView.VERTICAL, false)
|
||||
recyclerView.adapter = messageActionsEpoxyController.adapter
|
||||
// Disable item animation
|
||||
|
@ -69,12 +68,12 @@ class MessageActionsBottomSheet : VectorBaseBottomSheetDialogFragment(), Message
|
|||
messageActionsEpoxyController.listener = this
|
||||
}
|
||||
|
||||
override fun didSelectMenuAction(simpleAction: SimpleAction) {
|
||||
if (simpleAction is SimpleAction.ReportContent) {
|
||||
override fun didSelectMenuAction(eventAction: EventSharedAction) {
|
||||
if (eventAction is EventSharedAction.ReportContent) {
|
||||
// Toggle report menu
|
||||
viewModel.toggleReportMenu()
|
||||
viewModel.handle(MessageActionsAction.ToggleReportMenu)
|
||||
} else {
|
||||
messageActionsStore.post(simpleAction)
|
||||
sharedActionViewModel.post(eventAction)
|
||||
dismiss()
|
||||
}
|
||||
}
|
||||
|
|
|
@ -84,7 +84,7 @@ class MessageActionsEpoxyController @Inject constructor(private val stringProvid
|
|||
selecteds(state.quickStates.invoke().map { it.isSelected })
|
||||
listener(object : BottomSheetItemQuickReactions.Listener {
|
||||
override fun didSelect(emoji: String, selected: Boolean) {
|
||||
listener?.didSelectMenuAction(SimpleAction.QuickReact(state.eventId, emoji, selected))
|
||||
listener?.didSelectMenuAction(EventSharedAction.QuickReact(state.eventId, emoji, selected))
|
||||
}
|
||||
})
|
||||
}
|
||||
|
@ -101,17 +101,17 @@ class MessageActionsEpoxyController @Inject constructor(private val stringProvid
|
|||
id("action_$index")
|
||||
iconRes(action.iconResId)
|
||||
textRes(action.titleRes)
|
||||
showExpand(action is SimpleAction.ReportContent)
|
||||
showExpand(action is EventSharedAction.ReportContent)
|
||||
expanded(state.expendedReportContentMenu)
|
||||
listener(View.OnClickListener { listener?.didSelectMenuAction(action) })
|
||||
}
|
||||
|
||||
if (action is SimpleAction.ReportContent && state.expendedReportContentMenu) {
|
||||
if (action is EventSharedAction.ReportContent && state.expendedReportContentMenu) {
|
||||
// Special case for report content menu: add the submenu
|
||||
listOf(
|
||||
SimpleAction.ReportContentSpam(action.eventId, action.senderId),
|
||||
SimpleAction.ReportContentInappropriate(action.eventId, action.senderId),
|
||||
SimpleAction.ReportContentCustom(action.eventId, action.senderId)
|
||||
EventSharedAction.ReportContentSpam(action.eventId, action.senderId),
|
||||
EventSharedAction.ReportContentInappropriate(action.eventId, action.senderId),
|
||||
EventSharedAction.ReportContentCustom(action.eventId, action.senderId)
|
||||
).forEachIndexed { indexReport, actionReport ->
|
||||
bottomSheetItemAction {
|
||||
id("actionReport_$indexReport")
|
||||
|
@ -126,6 +126,6 @@ class MessageActionsEpoxyController @Inject constructor(private val stringProvid
|
|||
}
|
||||
|
||||
interface MessageActionsEpoxyControllerListener {
|
||||
fun didSelectMenuAction(simpleAction: SimpleAction)
|
||||
fun didSelectMenuAction(eventAction: EventSharedAction)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -42,8 +42,7 @@ import im.vector.riotx.features.home.room.detail.timeline.format.NoticeEventForm
|
|||
import im.vector.riotx.features.home.room.detail.timeline.item.MessageInformationData
|
||||
import im.vector.riotx.features.html.EventHtmlRenderer
|
||||
import java.text.SimpleDateFormat
|
||||
import java.util.Date
|
||||
import java.util.Locale
|
||||
import java.util.*
|
||||
|
||||
/**
|
||||
* Quick reactions state
|
||||
|
@ -62,7 +61,7 @@ data class MessageActionState(
|
|||
// For quick reactions
|
||||
val quickStates: Async<List<ToggleState>> = Uninitialized,
|
||||
// For actions
|
||||
val actions: Async<List<SimpleAction>> = Uninitialized,
|
||||
val actions: Async<List<EventSharedAction>> = Uninitialized,
|
||||
val expendedReportContentMenu: Boolean = false
|
||||
) : MvRxState {
|
||||
|
||||
|
@ -78,7 +77,7 @@ data class MessageActionState(
|
|||
}
|
||||
|
||||
/**
|
||||
* Information related to an event and used to display preview in contextual bottomsheet.
|
||||
* Information related to an event and used to display preview in contextual bottom sheet.
|
||||
*/
|
||||
class MessageActionsViewModel @AssistedInject constructor(@Assisted
|
||||
initialState: MessageActionState,
|
||||
|
@ -86,7 +85,7 @@ class MessageActionsViewModel @AssistedInject constructor(@Assisted
|
|||
private val session: Session,
|
||||
private val noticeEventFormatter: NoticeEventFormatter,
|
||||
private val stringProvider: StringProvider
|
||||
) : VectorViewModel<MessageActionState>(initialState) {
|
||||
) : VectorViewModel<MessageActionState, MessageActionsAction>(initialState) {
|
||||
|
||||
private val eventId = initialState.eventId
|
||||
private val informationData = initialState.informationData
|
||||
|
@ -113,7 +112,13 @@ class MessageActionsViewModel @AssistedInject constructor(@Assisted
|
|||
observeEventAction()
|
||||
}
|
||||
|
||||
fun toggleReportMenu() = withState {
|
||||
override fun handle(action: MessageActionsAction) {
|
||||
when (action) {
|
||||
MessageActionsAction.ToggleReportMenu -> toggleReportMenu()
|
||||
}
|
||||
}
|
||||
|
||||
private fun toggleReportMenu() = withState {
|
||||
setState {
|
||||
copy(
|
||||
expendedReportContentMenu = it.expendedReportContentMenu.not()
|
||||
|
@ -184,63 +189,63 @@ class MessageActionsViewModel @AssistedInject constructor(@Assisted
|
|||
}
|
||||
}
|
||||
|
||||
private fun actionsForEvent(optionalEvent: Optional<TimelineEvent>): List<SimpleAction> {
|
||||
private fun actionsForEvent(optionalEvent: Optional<TimelineEvent>): List<EventSharedAction> {
|
||||
val event = optionalEvent.getOrNull() ?: return emptyList()
|
||||
|
||||
val messageContent: MessageContent? = event.annotations?.editSummary?.aggregatedContent.toModel()
|
||||
?: event.root.getClearContent().toModel()
|
||||
val type = messageContent?.type
|
||||
|
||||
return arrayListOf<SimpleAction>().apply {
|
||||
return arrayListOf<EventSharedAction>().apply {
|
||||
if (event.root.sendState.hasFailed()) {
|
||||
if (canRetry(event)) {
|
||||
add(SimpleAction.Resend(eventId))
|
||||
add(EventSharedAction.Resend(eventId))
|
||||
}
|
||||
add(SimpleAction.Remove(eventId))
|
||||
add(EventSharedAction.Remove(eventId))
|
||||
} else if (event.root.sendState.isSending()) {
|
||||
// TODO is uploading attachment?
|
||||
if (canCancel(event)) {
|
||||
add(SimpleAction.Cancel(eventId))
|
||||
add(EventSharedAction.Cancel(eventId))
|
||||
}
|
||||
} else if (event.root.sendState == SendState.SYNCED) {
|
||||
if (!event.root.isRedacted()) {
|
||||
if (canReply(event, messageContent)) {
|
||||
add(SimpleAction.Reply(eventId))
|
||||
add(EventSharedAction.Reply(eventId))
|
||||
}
|
||||
|
||||
if (canEdit(event, session.myUserId)) {
|
||||
add(SimpleAction.Edit(eventId))
|
||||
add(EventSharedAction.Edit(eventId))
|
||||
}
|
||||
|
||||
if (canRedact(event, session.myUserId)) {
|
||||
add(SimpleAction.Delete(eventId))
|
||||
add(EventSharedAction.Delete(eventId))
|
||||
}
|
||||
|
||||
if (canCopy(type)) {
|
||||
// TODO copy images? html? see ClipBoard
|
||||
add(SimpleAction.Copy(messageContent!!.body))
|
||||
add(EventSharedAction.Copy(messageContent!!.body))
|
||||
}
|
||||
|
||||
if (event.canReact()) {
|
||||
add(SimpleAction.AddReaction(eventId))
|
||||
add(EventSharedAction.AddReaction(eventId))
|
||||
}
|
||||
|
||||
if (canQuote(event, messageContent)) {
|
||||
add(SimpleAction.Quote(eventId))
|
||||
add(EventSharedAction.Quote(eventId))
|
||||
}
|
||||
|
||||
if (canViewReactions(event)) {
|
||||
add(SimpleAction.ViewReactions(informationData))
|
||||
add(EventSharedAction.ViewReactions(informationData))
|
||||
}
|
||||
|
||||
if (event.hasBeenEdited()) {
|
||||
add(SimpleAction.ViewEditHistory(informationData))
|
||||
add(EventSharedAction.ViewEditHistory(informationData))
|
||||
}
|
||||
|
||||
if (canShare(type)) {
|
||||
if (messageContent is MessageImageContent) {
|
||||
session.contentUrlResolver().resolveFullSize(messageContent.url)?.let { url ->
|
||||
add(SimpleAction.Share(url))
|
||||
add(EventSharedAction.Share(url))
|
||||
}
|
||||
}
|
||||
// TODO
|
||||
|
@ -253,17 +258,17 @@ class MessageActionsViewModel @AssistedInject constructor(@Assisted
|
|||
}
|
||||
}
|
||||
|
||||
add(SimpleAction.ViewSource(event.root.toContentStringWithIndent()))
|
||||
add(EventSharedAction.ViewSource(event.root.toContentStringWithIndent()))
|
||||
if (event.isEncrypted()) {
|
||||
val decryptedContent = event.root.toClearContentStringWithIndent()
|
||||
?: stringProvider.getString(R.string.encryption_information_decryption_error)
|
||||
add(SimpleAction.ViewDecryptedSource(decryptedContent))
|
||||
add(EventSharedAction.ViewDecryptedSource(decryptedContent))
|
||||
}
|
||||
add(SimpleAction.CopyPermalink(eventId))
|
||||
add(EventSharedAction.CopyPermalink(eventId))
|
||||
|
||||
if (session.myUserId != event.root.senderId && event.root.getClearType() == EventType.MESSAGE) {
|
||||
// not sent by me
|
||||
add(SimpleAction.ReportContent(eventId, event.root.senderId))
|
||||
add(EventSharedAction.ReportContent(eventId, event.root.senderId))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -15,13 +15,10 @@
|
|||
*/
|
||||
package im.vector.riotx.features.home.room.detail.timeline.action
|
||||
|
||||
import androidx.lifecycle.ViewModel
|
||||
import im.vector.riotx.core.utils.PublishDataSource
|
||||
import im.vector.riotx.core.utils.MutableDataSource
|
||||
import im.vector.riotx.core.platform.VectorSharedActionViewModel
|
||||
import javax.inject.Inject
|
||||
|
||||
/**
|
||||
* Activity shared view model to handle message actions
|
||||
*/
|
||||
class MessageActionsDispatcher constructor(
|
||||
private val dataSource: MutableDataSource<SimpleAction> = PublishDataSource()
|
||||
) : ViewModel(), MutableDataSource<SimpleAction> by dataSource
|
||||
class MessageSharedActionViewModel @Inject constructor() : VectorSharedActionViewModel<EventSharedAction>()
|
|
@ -26,11 +26,12 @@ import im.vector.matrix.android.api.session.events.model.toModel
|
|||
import im.vector.matrix.android.api.session.room.model.message.MessageContent
|
||||
import im.vector.matrix.android.api.session.room.model.message.isReply
|
||||
import im.vector.matrix.android.internal.crypto.algorithms.olm.OlmDecryptionResult
|
||||
import im.vector.riotx.core.platform.VectorViewModel
|
||||
import im.vector.riotx.core.date.VectorDateFormatter
|
||||
import im.vector.riotx.core.platform.EmptyAction
|
||||
import im.vector.riotx.core.platform.VectorViewModel
|
||||
import im.vector.riotx.features.home.room.detail.timeline.action.TimelineEventFragmentArgs
|
||||
import timber.log.Timber
|
||||
import java.util.UUID
|
||||
import java.util.*
|
||||
|
||||
data class ViewEditHistoryViewState(
|
||||
val eventId: String,
|
||||
|
@ -46,7 +47,7 @@ class ViewEditHistoryViewModel @AssistedInject constructor(@Assisted
|
|||
initialState: ViewEditHistoryViewState,
|
||||
val session: Session,
|
||||
val dateFormatter: VectorDateFormatter
|
||||
) : VectorViewModel<ViewEditHistoryViewState>(initialState) {
|
||||
) : VectorViewModel<ViewEditHistoryViewState, EmptyAction>(initialState) {
|
||||
|
||||
private val roomId = initialState.roomId
|
||||
private val eventId = initialState.eventId
|
||||
|
@ -115,4 +116,8 @@ class ViewEditHistoryViewModel @AssistedInject constructor(@Assisted
|
|||
}
|
||||
})
|
||||
}
|
||||
|
||||
override fun handle(action: EmptyAction) {
|
||||
// No op
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,20 +16,16 @@
|
|||
|
||||
package im.vector.riotx.features.home.room.detail.timeline.reactions
|
||||
|
||||
import com.airbnb.mvrx.Async
|
||||
import com.airbnb.mvrx.FragmentViewModelContext
|
||||
import com.airbnb.mvrx.MvRxState
|
||||
import com.airbnb.mvrx.MvRxViewModelFactory
|
||||
import com.airbnb.mvrx.Uninitialized
|
||||
import com.airbnb.mvrx.ViewModelContext
|
||||
import com.airbnb.mvrx.*
|
||||
import com.squareup.inject.assisted.Assisted
|
||||
import com.squareup.inject.assisted.AssistedInject
|
||||
import im.vector.matrix.android.api.session.Session
|
||||
import im.vector.matrix.android.api.session.room.model.ReactionAggregatedSummary
|
||||
import im.vector.matrix.rx.RxRoom
|
||||
import im.vector.matrix.rx.unwrap
|
||||
import im.vector.riotx.core.platform.VectorViewModel
|
||||
import im.vector.riotx.core.date.VectorDateFormatter
|
||||
import im.vector.riotx.core.platform.EmptyAction
|
||||
import im.vector.riotx.core.platform.VectorViewModel
|
||||
import im.vector.riotx.features.home.room.detail.timeline.action.TimelineEventFragmentArgs
|
||||
import io.reactivex.Observable
|
||||
import io.reactivex.Single
|
||||
|
@ -55,15 +51,15 @@ data class ReactionInfo(
|
|||
* Used to display the list of members that reacted to a given event
|
||||
*/
|
||||
class ViewReactionsViewModel @AssistedInject constructor(@Assisted
|
||||
initialState: DisplayReactionsViewState,
|
||||
initialState: DisplayReactionsViewState,
|
||||
private val session: Session,
|
||||
private val dateFormatter: VectorDateFormatter
|
||||
) : VectorViewModel<DisplayReactionsViewState>(initialState) {
|
||||
) : VectorViewModel<DisplayReactionsViewState, EmptyAction>(initialState) {
|
||||
|
||||
private val roomId = initialState.roomId
|
||||
private val eventId = initialState.eventId
|
||||
private val room = session.getRoom(roomId)
|
||||
?: throw IllegalStateException("Shouldn't use this ViewModel without a room")
|
||||
?: throw IllegalStateException("Shouldn't use this ViewModel without a room")
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -103,7 +99,7 @@ class ViewReactionsViewModel @AssistedInject constructor(@Assisted
|
|||
.fromIterable(summary.sourceEvents)
|
||||
.map {
|
||||
val event = room.getTimeLineEvent(it)
|
||||
?: throw RuntimeException("Your eventId is not valid")
|
||||
?: throw RuntimeException("Your eventId is not valid")
|
||||
ReactionInfo(
|
||||
event.root.eventId!!,
|
||||
summary.key,
|
||||
|
@ -115,4 +111,8 @@ class ViewReactionsViewModel @AssistedInject constructor(@Assisted
|
|||
}
|
||||
}.toList()
|
||||
}
|
||||
|
||||
override fun handle(action: EmptyAction) {
|
||||
// No op
|
||||
}
|
||||
}
|
||||
|
|
|
@ -18,14 +18,15 @@ package im.vector.riotx.features.home.room.list
|
|||
|
||||
import im.vector.matrix.android.api.session.room.model.RoomSummary
|
||||
import im.vector.matrix.android.api.session.room.notification.RoomNotificationState
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class RoomListActions {
|
||||
data class SelectRoom(val roomSummary: RoomSummary) : RoomListActions()
|
||||
data class ToggleCategory(val category: RoomCategory) : RoomListActions()
|
||||
data class AcceptInvitation(val roomSummary: RoomSummary) : RoomListActions()
|
||||
data class RejectInvitation(val roomSummary: RoomSummary) : RoomListActions()
|
||||
data class FilterWith(val filter: String) : RoomListActions()
|
||||
data class ChangeRoomNotificationState(val roomId: String, val notificationState: RoomNotificationState) : RoomListActions()
|
||||
data class LeaveRoom(val roomId: String) : RoomListActions()
|
||||
object MarkAllRoomsRead : RoomListActions()
|
||||
sealed class RoomListAction : VectorViewModelAction {
|
||||
data class SelectRoom(val roomSummary: RoomSummary) : RoomListAction()
|
||||
data class ToggleCategory(val category: RoomCategory) : RoomListAction()
|
||||
data class AcceptInvitation(val roomSummary: RoomSummary) : RoomListAction()
|
||||
data class RejectInvitation(val roomSummary: RoomSummary) : RoomListAction()
|
||||
data class FilterWith(val filter: String) : RoomListAction()
|
||||
data class ChangeRoomNotificationState(val roomId: String, val notificationState: RoomNotificationState) : RoomListAction()
|
||||
data class LeaveRoom(val roomId: String) : RoomListAction()
|
||||
object MarkAllRoomsRead : RoomListAction()
|
||||
}
|
|
@ -24,7 +24,6 @@ import androidx.annotation.StringRes
|
|||
import androidx.appcompat.app.AlertDialog
|
||||
import androidx.core.content.ContextCompat
|
||||
import androidx.core.view.isVisible
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import com.airbnb.mvrx.*
|
||||
|
@ -39,9 +38,9 @@ import im.vector.riotx.core.error.ErrorFormatter
|
|||
import im.vector.riotx.core.platform.OnBackPressed
|
||||
import im.vector.riotx.core.platform.StateView
|
||||
import im.vector.riotx.core.platform.VectorBaseFragment
|
||||
import im.vector.riotx.features.home.room.list.actions.RoomListQuickActions
|
||||
import im.vector.riotx.features.home.room.list.actions.RoomListQuickActionsSharedAction
|
||||
import im.vector.riotx.features.home.room.list.actions.RoomListQuickActionsBottomSheet
|
||||
import im.vector.riotx.features.home.room.list.actions.RoomListQuickActionsStore
|
||||
import im.vector.riotx.features.home.room.list.actions.RoomListQuickActionsSharedActionViewModel
|
||||
import im.vector.riotx.features.home.room.list.widget.FabMenuView
|
||||
import im.vector.riotx.features.notifications.NotificationDrawerManager
|
||||
import im.vector.riotx.features.share.SharedData
|
||||
|
@ -72,7 +71,7 @@ class RoomListFragment @Inject constructor(
|
|||
SHARE(/* Not used */ 0)
|
||||
}
|
||||
|
||||
private lateinit var quickActionsDispatcher: RoomListQuickActionsStore
|
||||
private lateinit var sharedActionViewModel: RoomListQuickActionsSharedActionViewModel
|
||||
private val roomListParams: RoomListParams by args()
|
||||
private val roomListViewModel: RoomListViewModel by fragmentViewModel()
|
||||
|
||||
|
@ -85,7 +84,7 @@ class RoomListFragment @Inject constructor(
|
|||
override fun onOptionsItemSelected(item: MenuItem): Boolean {
|
||||
when (item.itemId) {
|
||||
R.id.menu_home_mark_all_as_read -> {
|
||||
roomListViewModel.accept(RoomListActions.MarkAllRoomsRead)
|
||||
roomListViewModel.handle(RoomListAction.MarkAllRoomsRead)
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
@ -100,7 +99,7 @@ class RoomListFragment @Inject constructor(
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
quickActionsDispatcher = ViewModelProviders.of(requireActivity()).get(RoomListQuickActionsStore::class.java)
|
||||
sharedActionViewModel = activityViewModelProvider.get(RoomListQuickActionsSharedActionViewModel::class.java)
|
||||
setupCreateRoomButton()
|
||||
setupRecyclerView()
|
||||
roomListViewModel.subscribe { renderState(it) }
|
||||
|
@ -118,7 +117,7 @@ class RoomListFragment @Inject constructor(
|
|||
|
||||
createChatFabMenu.listener = this
|
||||
|
||||
quickActionsDispatcher
|
||||
sharedActionViewModel
|
||||
.observe()
|
||||
.subscribe { handleQuickActions(it) }
|
||||
.disposeOnDestroy()
|
||||
|
@ -183,7 +182,7 @@ class RoomListFragment @Inject constructor(
|
|||
// Scroll the list to top
|
||||
roomListEpoxyRecyclerView.scrollToPosition(0)
|
||||
|
||||
roomListViewModel.accept(RoomListActions.FilterWith(filter))
|
||||
roomListViewModel.handle(RoomListAction.FilterWith(filter))
|
||||
}
|
||||
|
||||
override fun openRoomDirectory(initialFilter: String) {
|
||||
|
@ -216,29 +215,29 @@ class RoomListFragment @Inject constructor(
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleQuickActions(quickActions: RoomListQuickActions) {
|
||||
when (quickActions) {
|
||||
is RoomListQuickActions.NotificationsAllNoisy -> {
|
||||
roomListViewModel.accept(RoomListActions.ChangeRoomNotificationState(quickActions.roomId, RoomNotificationState.ALL_MESSAGES_NOISY))
|
||||
private fun handleQuickActions(quickAction: RoomListQuickActionsSharedAction) {
|
||||
when (quickAction) {
|
||||
is RoomListQuickActionsSharedAction.NotificationsAllNoisy -> {
|
||||
roomListViewModel.handle(RoomListAction.ChangeRoomNotificationState(quickAction.roomId, RoomNotificationState.ALL_MESSAGES_NOISY))
|
||||
}
|
||||
is RoomListQuickActions.NotificationsAll -> {
|
||||
roomListViewModel.accept(RoomListActions.ChangeRoomNotificationState(quickActions.roomId, RoomNotificationState.ALL_MESSAGES))
|
||||
is RoomListQuickActionsSharedAction.NotificationsAll -> {
|
||||
roomListViewModel.handle(RoomListAction.ChangeRoomNotificationState(quickAction.roomId, RoomNotificationState.ALL_MESSAGES))
|
||||
}
|
||||
is RoomListQuickActions.NotificationsMentionsOnly -> {
|
||||
roomListViewModel.accept(RoomListActions.ChangeRoomNotificationState(quickActions.roomId, RoomNotificationState.MENTIONS_ONLY))
|
||||
is RoomListQuickActionsSharedAction.NotificationsMentionsOnly -> {
|
||||
roomListViewModel.handle(RoomListAction.ChangeRoomNotificationState(quickAction.roomId, RoomNotificationState.MENTIONS_ONLY))
|
||||
}
|
||||
is RoomListQuickActions.NotificationsMute -> {
|
||||
roomListViewModel.accept(RoomListActions.ChangeRoomNotificationState(quickActions.roomId, RoomNotificationState.MUTE))
|
||||
is RoomListQuickActionsSharedAction.NotificationsMute -> {
|
||||
roomListViewModel.handle(RoomListAction.ChangeRoomNotificationState(quickAction.roomId, RoomNotificationState.MUTE))
|
||||
}
|
||||
is RoomListQuickActions.Settings -> {
|
||||
is RoomListQuickActionsSharedAction.Settings -> {
|
||||
vectorBaseActivity.notImplemented("Opening room settings")
|
||||
}
|
||||
is RoomListQuickActions.Leave -> {
|
||||
is RoomListQuickActionsSharedAction.Leave -> {
|
||||
AlertDialog.Builder(requireContext())
|
||||
.setTitle(R.string.room_participants_leave_prompt_title)
|
||||
.setMessage(R.string.room_participants_leave_prompt_msg)
|
||||
.setPositiveButton(R.string.leave) { _, _ ->
|
||||
roomListViewModel.accept(RoomListActions.LeaveRoom(quickActions.roomId))
|
||||
roomListViewModel.handle(RoomListAction.LeaveRoom(quickAction.roomId))
|
||||
}
|
||||
.setNegativeButton(R.string.cancel, null)
|
||||
.show()
|
||||
|
@ -342,7 +341,7 @@ class RoomListFragment @Inject constructor(
|
|||
// RoomSummaryController.Callback **************************************************************
|
||||
|
||||
override fun onRoomClicked(room: RoomSummary) {
|
||||
roomListViewModel.accept(RoomListActions.SelectRoom(room))
|
||||
roomListViewModel.handle(RoomListAction.SelectRoom(room))
|
||||
}
|
||||
|
||||
override fun onRoomLongClicked(room: RoomSummary): Boolean {
|
||||
|
@ -354,16 +353,16 @@ class RoomListFragment @Inject constructor(
|
|||
|
||||
override fun onAcceptRoomInvitation(room: RoomSummary) {
|
||||
notificationDrawerManager.clearMemberShipNotificationForRoom(room.roomId)
|
||||
roomListViewModel.accept(RoomListActions.AcceptInvitation(room))
|
||||
roomListViewModel.handle(RoomListAction.AcceptInvitation(room))
|
||||
}
|
||||
|
||||
override fun onRejectRoomInvitation(room: RoomSummary) {
|
||||
notificationDrawerManager.clearMemberShipNotificationForRoom(room.roomId)
|
||||
roomListViewModel.accept(RoomListActions.RejectInvitation(room))
|
||||
roomListViewModel.handle(RoomListAction.RejectInvitation(room))
|
||||
}
|
||||
|
||||
override fun onToggleRoomCategory(roomCategory: RoomCategory) {
|
||||
roomListViewModel.accept(RoomListActions.ToggleCategory(roomCategory))
|
||||
roomListViewModel.handle(RoomListAction.ToggleCategory(roomCategory))
|
||||
}
|
||||
|
||||
override fun createRoom(initialName: String) {
|
||||
|
|
|
@ -36,7 +36,7 @@ class RoomListViewModel @Inject constructor(initialState: RoomListViewState,
|
|||
private val roomSummariesSource: DataSource<List<RoomSummary>>,
|
||||
private val alphabeticalRoomComparator: AlphabeticalRoomComparator,
|
||||
private val chronologicalRoomComparator: ChronologicalRoomComparator)
|
||||
: VectorViewModel<RoomListViewState>(initialState) {
|
||||
: VectorViewModel<RoomListViewState, RoomListAction>(initialState) {
|
||||
|
||||
interface Factory {
|
||||
fun create(initialState: RoomListViewState): RoomListViewModel
|
||||
|
@ -61,30 +61,30 @@ class RoomListViewModel @Inject constructor(initialState: RoomListViewState,
|
|||
observeRoomSummaries()
|
||||
}
|
||||
|
||||
fun accept(action: RoomListActions) {
|
||||
override fun handle(action: RoomListAction) {
|
||||
when (action) {
|
||||
is RoomListActions.SelectRoom -> handleSelectRoom(action)
|
||||
is RoomListActions.ToggleCategory -> handleToggleCategory(action)
|
||||
is RoomListActions.AcceptInvitation -> handleAcceptInvitation(action)
|
||||
is RoomListActions.RejectInvitation -> handleRejectInvitation(action)
|
||||
is RoomListActions.FilterWith -> handleFilter(action)
|
||||
is RoomListActions.MarkAllRoomsRead -> handleMarkAllRoomsRead()
|
||||
is RoomListActions.LeaveRoom -> handleLeaveRoom(action)
|
||||
is RoomListActions.ChangeRoomNotificationState -> handleChangeNotificationMode(action)
|
||||
is RoomListAction.SelectRoom -> handleSelectRoom(action)
|
||||
is RoomListAction.ToggleCategory -> handleToggleCategory(action)
|
||||
is RoomListAction.AcceptInvitation -> handleAcceptInvitation(action)
|
||||
is RoomListAction.RejectInvitation -> handleRejectInvitation(action)
|
||||
is RoomListAction.FilterWith -> handleFilter(action)
|
||||
is RoomListAction.MarkAllRoomsRead -> handleMarkAllRoomsRead()
|
||||
is RoomListAction.LeaveRoom -> handleLeaveRoom(action)
|
||||
is RoomListAction.ChangeRoomNotificationState -> handleChangeNotificationMode(action)
|
||||
}
|
||||
}
|
||||
|
||||
// PRIVATE METHODS *****************************************************************************
|
||||
|
||||
private fun handleSelectRoom(action: RoomListActions.SelectRoom) {
|
||||
private fun handleSelectRoom(action: RoomListAction.SelectRoom) {
|
||||
_viewEvents.post(RoomListViewEvents.SelectRoom(action.roomSummary.roomId))
|
||||
}
|
||||
|
||||
private fun handleToggleCategory(action: RoomListActions.ToggleCategory) = setState {
|
||||
private fun handleToggleCategory(action: RoomListAction.ToggleCategory) = setState {
|
||||
this.toggle(action.category)
|
||||
}
|
||||
|
||||
private fun handleFilter(action: RoomListActions.FilterWith) {
|
||||
private fun handleFilter(action: RoomListAction.FilterWith) {
|
||||
setState {
|
||||
copy(
|
||||
roomFilter = action.filter
|
||||
|
@ -112,7 +112,7 @@ class RoomListViewModel @Inject constructor(initialState: RoomListViewState,
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleAcceptInvitation(action: RoomListActions.AcceptInvitation) = withState { state ->
|
||||
private fun handleAcceptInvitation(action: RoomListAction.AcceptInvitation) = withState { state ->
|
||||
val roomId = action.roomSummary.roomId
|
||||
|
||||
if (state.joiningRoomsIds.contains(roomId) || state.rejectingRoomsIds.contains(roomId)) {
|
||||
|
@ -147,7 +147,7 @@ class RoomListViewModel @Inject constructor(initialState: RoomListViewState,
|
|||
})
|
||||
}
|
||||
|
||||
private fun handleRejectInvitation(action: RoomListActions.RejectInvitation) = withState { state ->
|
||||
private fun handleRejectInvitation(action: RoomListAction.RejectInvitation) = withState { state ->
|
||||
val roomId = action.roomSummary.roomId
|
||||
|
||||
if (state.joiningRoomsIds.contains(roomId) || state.rejectingRoomsIds.contains(roomId)) {
|
||||
|
@ -193,7 +193,7 @@ class RoomListViewModel @Inject constructor(initialState: RoomListViewState,
|
|||
?.let { session.markAllAsRead(it, object : MatrixCallback<Unit> {}) }
|
||||
}
|
||||
|
||||
private fun handleChangeNotificationMode(action: RoomListActions.ChangeRoomNotificationState) {
|
||||
private fun handleChangeNotificationMode(action: RoomListAction.ChangeRoomNotificationState) {
|
||||
session.getRoom(action.roomId)?.setRoomNotificationState(action.notificationState, object : MatrixCallback<Unit> {
|
||||
override fun onFailure(failure: Throwable) {
|
||||
_viewEvents.post(RoomListViewEvents.Failure(failure))
|
||||
|
@ -201,7 +201,7 @@ class RoomListViewModel @Inject constructor(initialState: RoomListViewState,
|
|||
})
|
||||
}
|
||||
|
||||
private fun handleLeaveRoom(action: RoomListActions.LeaveRoom) {
|
||||
private fun handleLeaveRoom(action: RoomListAction.LeaveRoom) {
|
||||
session.getRoom(action.roomId)?.leave(object : MatrixCallback<Unit> {
|
||||
override fun onFailure(failure: Throwable) {
|
||||
_viewEvents.post(RoomListViewEvents.Failure(failure))
|
||||
|
|
|
@ -21,7 +21,6 @@ import android.os.Parcelable
|
|||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import butterknife.BindView
|
||||
|
@ -45,7 +44,7 @@ data class RoomListActionsArgs(
|
|||
*/
|
||||
class RoomListQuickActionsBottomSheet : VectorBaseBottomSheetDialogFragment(), RoomListQuickActionsEpoxyController.Listener {
|
||||
|
||||
private lateinit var actionsDispatcher: RoomListQuickActionsStore
|
||||
private lateinit var sharedActionViewModel: RoomListQuickActionsSharedActionViewModel
|
||||
@Inject lateinit var roomListActionsViewModelFactory: RoomListQuickActionsViewModel.Factory
|
||||
@Inject lateinit var roomListActionsEpoxyController: RoomListQuickActionsEpoxyController
|
||||
@Inject lateinit var navigator: Navigator
|
||||
|
@ -69,7 +68,7 @@ class RoomListQuickActionsBottomSheet : VectorBaseBottomSheetDialogFragment(), R
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
actionsDispatcher = ViewModelProviders.of(requireActivity()).get(RoomListQuickActionsStore::class.java)
|
||||
sharedActionViewModel = activityViewModelProvider.get(RoomListQuickActionsSharedActionViewModel::class.java)
|
||||
recyclerView.layoutManager = LinearLayoutManager(requireContext(), RecyclerView.VERTICAL, false)
|
||||
recyclerView.adapter = roomListActionsEpoxyController.adapter
|
||||
// Disable item animation
|
||||
|
@ -82,8 +81,8 @@ class RoomListQuickActionsBottomSheet : VectorBaseBottomSheetDialogFragment(), R
|
|||
super.invalidate()
|
||||
}
|
||||
|
||||
override fun didSelectMenuAction(quickActions: RoomListQuickActions) {
|
||||
actionsDispatcher.post(quickActions)
|
||||
override fun didSelectMenuAction(quickAction: RoomListQuickActionsSharedAction) {
|
||||
sharedActionViewModel.post(quickAction)
|
||||
dismiss()
|
||||
}
|
||||
|
||||
|
|
|
@ -42,7 +42,7 @@ class RoomListQuickActionsEpoxyController @Inject constructor(private val avatar
|
|||
roomName(roomSummary.displayName)
|
||||
avatarUrl(roomSummary.avatarUrl)
|
||||
roomId(roomSummary.roomId)
|
||||
settingsClickListener(View.OnClickListener { listener?.didSelectMenuAction(RoomListQuickActions.Settings(roomSummary.roomId)) })
|
||||
settingsClickListener(View.OnClickListener { listener?.didSelectMenuAction(RoomListQuickActionsSharedAction.Settings(roomSummary.roomId)) })
|
||||
}
|
||||
|
||||
// Notifications
|
||||
|
@ -51,26 +51,26 @@ class RoomListQuickActionsEpoxyController @Inject constructor(private val avatar
|
|||
}
|
||||
|
||||
val selectedRoomState = state.roomNotificationState()
|
||||
RoomListQuickActions.NotificationsAllNoisy(roomSummary.roomId).toBottomSheetItem(0, selectedRoomState)
|
||||
RoomListQuickActions.NotificationsAll(roomSummary.roomId).toBottomSheetItem(1, selectedRoomState)
|
||||
RoomListQuickActions.NotificationsMentionsOnly(roomSummary.roomId).toBottomSheetItem(2, selectedRoomState)
|
||||
RoomListQuickActions.NotificationsMute(roomSummary.roomId).toBottomSheetItem(3, selectedRoomState)
|
||||
RoomListQuickActionsSharedAction.NotificationsAllNoisy(roomSummary.roomId).toBottomSheetItem(0, selectedRoomState)
|
||||
RoomListQuickActionsSharedAction.NotificationsAll(roomSummary.roomId).toBottomSheetItem(1, selectedRoomState)
|
||||
RoomListQuickActionsSharedAction.NotificationsMentionsOnly(roomSummary.roomId).toBottomSheetItem(2, selectedRoomState)
|
||||
RoomListQuickActionsSharedAction.NotificationsMute(roomSummary.roomId).toBottomSheetItem(3, selectedRoomState)
|
||||
|
||||
// Leave
|
||||
bottomSheetItemSeparator {
|
||||
id("leave_separator")
|
||||
}
|
||||
RoomListQuickActions.Leave(roomSummary.roomId).toBottomSheetItem(5)
|
||||
RoomListQuickActionsSharedAction.Leave(roomSummary.roomId).toBottomSheetItem(5)
|
||||
}
|
||||
|
||||
private fun RoomListQuickActions.toBottomSheetItem(index: Int, roomNotificationState: RoomNotificationState? = null) {
|
||||
private fun RoomListQuickActionsSharedAction.toBottomSheetItem(index: Int, roomNotificationState: RoomNotificationState? = null) {
|
||||
val selected = when (this) {
|
||||
is RoomListQuickActions.NotificationsAllNoisy -> roomNotificationState == RoomNotificationState.ALL_MESSAGES_NOISY
|
||||
is RoomListQuickActions.NotificationsAll -> roomNotificationState == RoomNotificationState.ALL_MESSAGES
|
||||
is RoomListQuickActions.NotificationsMentionsOnly -> roomNotificationState == RoomNotificationState.MENTIONS_ONLY
|
||||
is RoomListQuickActions.NotificationsMute -> roomNotificationState == RoomNotificationState.MUTE
|
||||
is RoomListQuickActions.Settings,
|
||||
is RoomListQuickActions.Leave -> false
|
||||
is RoomListQuickActionsSharedAction.NotificationsAllNoisy -> roomNotificationState == RoomNotificationState.ALL_MESSAGES_NOISY
|
||||
is RoomListQuickActionsSharedAction.NotificationsAll -> roomNotificationState == RoomNotificationState.ALL_MESSAGES
|
||||
is RoomListQuickActionsSharedAction.NotificationsMentionsOnly -> roomNotificationState == RoomNotificationState.MENTIONS_ONLY
|
||||
is RoomListQuickActionsSharedAction.NotificationsMute -> roomNotificationState == RoomNotificationState.MUTE
|
||||
is RoomListQuickActionsSharedAction.Settings,
|
||||
is RoomListQuickActionsSharedAction.Leave -> false
|
||||
}
|
||||
return bottomSheetItemAction {
|
||||
id("action_$index")
|
||||
|
@ -83,6 +83,6 @@ class RoomListQuickActionsEpoxyController @Inject constructor(private val avatar
|
|||
}
|
||||
|
||||
interface Listener {
|
||||
fun didSelectMenuAction(quickActions: RoomListQuickActions)
|
||||
fun didSelectMenuAction(quickAction: RoomListQuickActionsSharedAction)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -19,35 +19,40 @@ package im.vector.riotx.features.home.room.list.actions
|
|||
import androidx.annotation.DrawableRes
|
||||
import androidx.annotation.StringRes
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.platform.VectorSharedAction
|
||||
|
||||
sealed class RoomListQuickActions(@StringRes val titleRes: Int, @DrawableRes val iconResId: Int, val destructive: Boolean = false) {
|
||||
sealed class RoomListQuickActionsSharedAction(
|
||||
@StringRes val titleRes: Int,
|
||||
@DrawableRes val iconResId: Int,
|
||||
val destructive: Boolean = false)
|
||||
: VectorSharedAction {
|
||||
|
||||
data class NotificationsAllNoisy(val roomId: String) : RoomListQuickActions(
|
||||
data class NotificationsAllNoisy(val roomId: String) : RoomListQuickActionsSharedAction(
|
||||
R.string.room_list_quick_actions_notifications_all_noisy,
|
||||
R.drawable.ic_room_actions_notifications_all_noisy
|
||||
)
|
||||
|
||||
data class NotificationsAll(val roomId: String) : RoomListQuickActions(
|
||||
data class NotificationsAll(val roomId: String) : RoomListQuickActionsSharedAction(
|
||||
R.string.room_list_quick_actions_notifications_all,
|
||||
R.drawable.ic_room_actions_notifications_all
|
||||
)
|
||||
|
||||
data class NotificationsMentionsOnly(val roomId: String) : RoomListQuickActions(
|
||||
data class NotificationsMentionsOnly(val roomId: String) : RoomListQuickActionsSharedAction(
|
||||
R.string.room_list_quick_actions_notifications_mentions,
|
||||
R.drawable.ic_room_actions_notifications_mentions
|
||||
)
|
||||
|
||||
data class NotificationsMute(val roomId: String) : RoomListQuickActions(
|
||||
data class NotificationsMute(val roomId: String) : RoomListQuickActionsSharedAction(
|
||||
R.string.room_list_quick_actions_notifications_mute,
|
||||
R.drawable.ic_room_actions_notifications_mutes
|
||||
)
|
||||
|
||||
data class Settings(val roomId: String) : RoomListQuickActions(
|
||||
data class Settings(val roomId: String) : RoomListQuickActionsSharedAction(
|
||||
R.string.room_list_quick_actions_settings,
|
||||
R.drawable.ic_room_actions_settings
|
||||
)
|
||||
|
||||
data class Leave(val roomId: String) : RoomListQuickActions(
|
||||
data class Leave(val roomId: String) : RoomListQuickActionsSharedAction(
|
||||
R.string.room_list_quick_actions_leave,
|
||||
R.drawable.ic_room_actions_leave,
|
||||
true
|
|
@ -16,13 +16,10 @@
|
|||
*/
|
||||
package im.vector.riotx.features.home.room.list.actions
|
||||
|
||||
import androidx.lifecycle.ViewModel
|
||||
import im.vector.riotx.core.utils.PublishDataSource
|
||||
import im.vector.riotx.core.utils.MutableDataSource
|
||||
import im.vector.riotx.core.platform.VectorSharedActionViewModel
|
||||
import javax.inject.Inject
|
||||
|
||||
/**
|
||||
* Activity shared view model to handle room list quick actions
|
||||
*/
|
||||
class RoomListQuickActionsStore constructor(
|
||||
private val store: MutableDataSource<RoomListQuickActions> = PublishDataSource()
|
||||
) : ViewModel(), MutableDataSource<RoomListQuickActions> by store
|
||||
class RoomListQuickActionsSharedActionViewModel @Inject constructor() : VectorSharedActionViewModel<RoomListQuickActionsSharedAction>()
|
|
@ -15,17 +15,20 @@
|
|||
*/
|
||||
package im.vector.riotx.features.home.room.list.actions
|
||||
|
||||
import com.airbnb.mvrx.*
|
||||
import com.airbnb.mvrx.FragmentViewModelContext
|
||||
import com.airbnb.mvrx.MvRxViewModelFactory
|
||||
import com.airbnb.mvrx.ViewModelContext
|
||||
import com.squareup.inject.assisted.Assisted
|
||||
import com.squareup.inject.assisted.AssistedInject
|
||||
import im.vector.matrix.android.api.session.Session
|
||||
import im.vector.matrix.rx.rx
|
||||
import im.vector.matrix.rx.unwrap
|
||||
import im.vector.riotx.core.platform.EmptyAction
|
||||
import im.vector.riotx.core.platform.VectorViewModel
|
||||
|
||||
class RoomListQuickActionsViewModel @AssistedInject constructor(@Assisted initialState: RoomListQuickActionsState,
|
||||
session: Session
|
||||
) : VectorViewModel<RoomListQuickActionsState>(initialState) {
|
||||
) : VectorViewModel<RoomListQuickActionsState, EmptyAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -65,4 +68,8 @@ class RoomListQuickActionsViewModel @AssistedInject constructor(@Assisted initia
|
|||
copy(roomSummary = it)
|
||||
}
|
||||
}
|
||||
|
||||
override fun handle(action: EmptyAction) {
|
||||
// No op
|
||||
}
|
||||
}
|
||||
|
|
|
@ -17,12 +17,12 @@
|
|||
package im.vector.riotx.features.login
|
||||
|
||||
import im.vector.matrix.android.api.auth.data.Credentials
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class LoginActions {
|
||||
|
||||
data class UpdateHomeServer(val homeServerUrl: String) : LoginActions()
|
||||
data class Login(val login: String, val password: String) : LoginActions()
|
||||
data class SsoLoginSuccess(val credentials: Credentials) : LoginActions()
|
||||
data class NavigateTo(val target: LoginActivity.Navigation) : LoginActions()
|
||||
data class InitWith(val loginConfig: LoginConfig) : LoginActions()
|
||||
sealed class LoginAction : VectorViewModelAction {
|
||||
data class UpdateHomeServer(val homeServerUrl: String) : LoginAction()
|
||||
data class Login(val login: String, val password: String) : LoginAction()
|
||||
data class SsoLoginSuccess(val credentials: Credentials) : LoginAction()
|
||||
data class NavigateTo(val target: LoginActivity.Navigation) : LoginAction()
|
||||
data class InitWith(val loginConfig: LoginConfig) : LoginAction()
|
||||
}
|
|
@ -57,7 +57,7 @@ class LoginActivity : VectorBaseActivity() {
|
|||
// Get config extra
|
||||
val loginConfig = intent.getParcelableExtra<LoginConfig?>(EXTRA_CONFIG)
|
||||
if (loginConfig != null && isFirstCreation()) {
|
||||
loginViewModel.handle(LoginActions.InitWith(loginConfig))
|
||||
loginViewModel.handle(LoginAction.InitWith(loginConfig))
|
||||
}
|
||||
|
||||
loginViewModel.navigationLiveData.observeEvent(this) {
|
||||
|
|
|
@ -59,14 +59,14 @@ class LoginFragment @Inject constructor() : VectorBaseFragment() {
|
|||
homeServerField.focusChanges()
|
||||
.subscribe {
|
||||
if (!it) {
|
||||
viewModel.handle(LoginActions.UpdateHomeServer(homeServerField.text.toString()))
|
||||
viewModel.handle(LoginAction.UpdateHomeServer(homeServerField.text.toString()))
|
||||
}
|
||||
}
|
||||
.disposeOnDestroy()
|
||||
|
||||
homeServerField.setOnEditorActionListener { _, actionId, _ ->
|
||||
if (actionId == EditorInfo.IME_ACTION_DONE) {
|
||||
viewModel.handle(LoginActions.UpdateHomeServer(homeServerField.text.toString()))
|
||||
viewModel.handle(LoginAction.UpdateHomeServer(homeServerField.text.toString()))
|
||||
return@setOnEditorActionListener true
|
||||
}
|
||||
return@setOnEditorActionListener false
|
||||
|
@ -78,7 +78,7 @@ class LoginFragment @Inject constructor() : VectorBaseFragment() {
|
|||
} else {
|
||||
homeServerField.setText(ServerUrlsRepository.getDefaultHomeServerUrl(requireContext()))
|
||||
}
|
||||
viewModel.handle(LoginActions.UpdateHomeServer(homeServerField.text.toString()))
|
||||
viewModel.handle(LoginAction.UpdateHomeServer(homeServerField.text.toString()))
|
||||
}
|
||||
|
||||
private fun setupNotice() {
|
||||
|
@ -93,7 +93,7 @@ class LoginFragment @Inject constructor() : VectorBaseFragment() {
|
|||
val login = loginField.text?.trim().toString()
|
||||
val password = passwordField.text?.trim().toString()
|
||||
|
||||
viewModel.handle(LoginActions.Login(login, password))
|
||||
viewModel.handle(LoginAction.Login(login, password))
|
||||
}
|
||||
|
||||
private fun setupAuthButton() {
|
||||
|
@ -114,7 +114,7 @@ class LoginFragment @Inject constructor() : VectorBaseFragment() {
|
|||
}
|
||||
|
||||
private fun openSso() {
|
||||
viewModel.handle(LoginActions.NavigateTo(LoginActivity.Navigation.OpenSsoLoginFallback))
|
||||
viewModel.handle(LoginAction.NavigateTo(LoginActivity.Navigation.OpenSsoLoginFallback))
|
||||
}
|
||||
|
||||
private fun setupPasswordReveal() {
|
||||
|
|
|
@ -143,7 +143,7 @@ class LoginSsoFallbackFragment @Inject constructor() : VectorBaseFragment(), OnB
|
|||
super.onReceivedError(view, errorCode, description, failingUrl)
|
||||
|
||||
// on error case, close this fragment
|
||||
viewModel.handle(LoginActions.NavigateTo(LoginActivity.Navigation.GoBack))
|
||||
viewModel.handle(LoginAction.NavigateTo(LoginActivity.Navigation.GoBack))
|
||||
}
|
||||
|
||||
override fun onPageStarted(view: WebView?, url: String?, favicon: Bitmap?) {
|
||||
|
@ -253,7 +253,7 @@ class LoginSsoFallbackFragment @Inject constructor() : VectorBaseFragment(), OnB
|
|||
refreshToken = null
|
||||
)
|
||||
|
||||
viewModel.handle(LoginActions.SsoLoginSuccess(safeCredentials))
|
||||
viewModel.handle(LoginAction.SsoLoginSuccess(safeCredentials))
|
||||
}
|
||||
}
|
||||
} catch (e: Exception) {
|
||||
|
@ -278,7 +278,7 @@ class LoginSsoFallbackFragment @Inject constructor() : VectorBaseFragment(), OnB
|
|||
refreshToken = null
|
||||
)
|
||||
|
||||
viewModel.handle(LoginActions.SsoLoginSuccess(credentials))
|
||||
viewModel.handle(LoginAction.SsoLoginSuccess(credentials))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -42,7 +42,7 @@ class LoginViewModel @AssistedInject constructor(@Assisted initialState: LoginVi
|
|||
private val activeSessionHolder: ActiveSessionHolder,
|
||||
private val pushRuleTriggerListener: PushRuleTriggerListener,
|
||||
private val sessionListener: SessionListener)
|
||||
: VectorViewModel<LoginViewState>(initialState) {
|
||||
: VectorViewModel<LoginViewState, LoginAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -67,21 +67,21 @@ class LoginViewModel @AssistedInject constructor(@Assisted initialState: LoginVi
|
|||
private var homeServerConnectionConfig: HomeServerConnectionConfig? = null
|
||||
private var currentTask: Cancelable? = null
|
||||
|
||||
fun handle(action: LoginActions) {
|
||||
override fun handle(action: LoginAction) {
|
||||
when (action) {
|
||||
is LoginActions.InitWith -> handleInitWith(action)
|
||||
is LoginActions.UpdateHomeServer -> handleUpdateHomeserver(action)
|
||||
is LoginActions.Login -> handleLogin(action)
|
||||
is LoginActions.SsoLoginSuccess -> handleSsoLoginSuccess(action)
|
||||
is LoginActions.NavigateTo -> handleNavigation(action)
|
||||
is LoginAction.InitWith -> handleInitWith(action)
|
||||
is LoginAction.UpdateHomeServer -> handleUpdateHomeserver(action)
|
||||
is LoginAction.Login -> handleLogin(action)
|
||||
is LoginAction.SsoLoginSuccess -> handleSsoLoginSuccess(action)
|
||||
is LoginAction.NavigateTo -> handleNavigation(action)
|
||||
}
|
||||
}
|
||||
|
||||
private fun handleInitWith(action: LoginActions.InitWith) {
|
||||
private fun handleInitWith(action: LoginAction.InitWith) {
|
||||
loginConfig = action.loginConfig
|
||||
}
|
||||
|
||||
private fun handleLogin(action: LoginActions.Login) {
|
||||
private fun handleLogin(action: LoginAction.Login) {
|
||||
val homeServerConnectionConfigFinal = homeServerConnectionConfig
|
||||
|
||||
if (homeServerConnectionConfigFinal == null) {
|
||||
|
@ -124,7 +124,7 @@ class LoginViewModel @AssistedInject constructor(@Assisted initialState: LoginVi
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleSsoLoginSuccess(action: LoginActions.SsoLoginSuccess) {
|
||||
private fun handleSsoLoginSuccess(action: LoginAction.SsoLoginSuccess) {
|
||||
val homeServerConnectionConfigFinal = homeServerConnectionConfig
|
||||
|
||||
if (homeServerConnectionConfigFinal == null) {
|
||||
|
@ -137,7 +137,7 @@ class LoginViewModel @AssistedInject constructor(@Assisted initialState: LoginVi
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleUpdateHomeserver(action: LoginActions.UpdateHomeServer) = withState { state ->
|
||||
private fun handleUpdateHomeserver(action: LoginAction.UpdateHomeServer) = withState { state ->
|
||||
|
||||
var newConfig: HomeServerConnectionConfig? = null
|
||||
Try {
|
||||
|
@ -197,7 +197,7 @@ class LoginViewModel @AssistedInject constructor(@Assisted initialState: LoginVi
|
|||
}
|
||||
}
|
||||
|
||||
private fun handleNavigation(action: LoginActions.NavigateTo) {
|
||||
private fun handleNavigation(action: LoginAction.NavigateTo) {
|
||||
_navigationLiveData.postValue(LiveEvent(action.target))
|
||||
}
|
||||
|
||||
|
|
|
@ -16,7 +16,6 @@
|
|||
package im.vector.riotx.features.reactions
|
||||
|
||||
import android.os.Bundle
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.platform.VectorBaseFragment
|
||||
|
@ -30,9 +29,7 @@ class EmojiChooserFragment @Inject constructor() : VectorBaseFragment() {
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
viewModel = activity?.run {
|
||||
ViewModelProviders.of(this, viewModelFactory).get(EmojiChooserViewModel::class.java)
|
||||
} ?: throw Exception("Invalid Activity")
|
||||
viewModel = activityViewModelProvider.get(EmojiChooserViewModel::class.java)
|
||||
viewModel.initWithContext(context!!)
|
||||
(view as? RecyclerView)?.let {
|
||||
it.adapter = viewModel.adapter
|
||||
|
|
|
@ -27,7 +27,6 @@ import android.widget.SearchView
|
|||
import androidx.appcompat.widget.Toolbar
|
||||
import androidx.core.view.isVisible
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import com.airbnb.mvrx.viewModel
|
||||
import com.google.android.material.tabs.TabLayout
|
||||
import com.jakewharton.rxbinding3.widget.queryTextChanges
|
||||
|
@ -63,7 +62,7 @@ class EmojiReactionPickerActivity : VectorBaseActivity(),
|
|||
|
||||
@Inject lateinit var emojiCompatFontProvider: EmojiCompatFontProvider
|
||||
|
||||
val searchResultViewModel: EmojiSearchResultViewModel by viewModel()
|
||||
private val searchResultViewModel: EmojiSearchResultViewModel by viewModel()
|
||||
|
||||
private var tabLayoutSelectionListener = object : TabLayout.OnTabSelectedListener {
|
||||
override fun onTabReselected(tab: TabLayout.Tab) {
|
||||
|
@ -90,7 +89,7 @@ class EmojiReactionPickerActivity : VectorBaseActivity(),
|
|||
|
||||
tabLayout = findViewById(R.id.tabs)
|
||||
|
||||
viewModel = ViewModelProviders.of(this, viewModelFactory).get(EmojiChooserViewModel::class.java)
|
||||
viewModel = viewModelProvider.get(EmojiChooserViewModel::class.java)
|
||||
|
||||
viewModel.eventId = intent.getStringExtra(EXTRA_EVENT_ID)
|
||||
|
||||
|
@ -201,7 +200,7 @@ class EmojiReactionPickerActivity : VectorBaseActivity(),
|
|||
tabLayout.isVisible = false
|
||||
emojiPickerWholeListFragmentContainer.isVisible = false
|
||||
emojiPickerFilteredListFragmentContainer.isVisible = true
|
||||
searchResultViewModel.updateQuery(query)
|
||||
searchResultViewModel.handle(EmojiSearchAction.UpdateQuery(query))
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,23 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.reactions
|
||||
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class EmojiSearchAction : VectorViewModelAction {
|
||||
data class UpdateQuery(val queryString: String) : EmojiSearchAction()
|
||||
}
|
|
@ -16,7 +16,6 @@
|
|||
package im.vector.riotx.features.reactions
|
||||
|
||||
import android.os.Bundle
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.recyclerview.widget.DividerItemDecoration
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
|
@ -41,7 +40,7 @@ class EmojiSearchResultFragment @Inject constructor(
|
|||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
|
||||
sharedViewModel = ViewModelProviders.of(requireActivity(), viewModelFactory).get(EmojiChooserViewModel::class.java)
|
||||
sharedViewModel = activityViewModelProvider.get(EmojiChooserViewModel::class.java)
|
||||
|
||||
epoxyController.listener = object : ReactionClickListener {
|
||||
override fun onReactionSelected(reaction: String) {
|
||||
|
|
|
@ -26,17 +26,23 @@ data class EmojiSearchResultViewState(
|
|||
) : MvRxState
|
||||
|
||||
class EmojiSearchResultViewModel(val dataSource: EmojiDataSource, initialState: EmojiSearchResultViewState)
|
||||
: VectorViewModel<EmojiSearchResultViewState>(initialState) {
|
||||
: VectorViewModel<EmojiSearchResultViewState, EmojiSearchAction>(initialState) {
|
||||
|
||||
fun updateQuery(queryString: String) {
|
||||
override fun handle(action: EmojiSearchAction) {
|
||||
when (action) {
|
||||
is EmojiSearchAction.UpdateQuery -> updateQuery(action)
|
||||
}
|
||||
}
|
||||
|
||||
private fun updateQuery(action: EmojiSearchAction.UpdateQuery) {
|
||||
setState {
|
||||
copy(
|
||||
query = queryString,
|
||||
query = action.queryString,
|
||||
results = dataSource.rawData?.emojis?.toList()
|
||||
?.map { it.second }
|
||||
?.filter {
|
||||
it.name.contains(queryString, true)
|
||||
|| queryString.split("\\s".toRegex()).fold(true, { prev, q ->
|
||||
it.name.contains(action.queryString, true)
|
||||
|| action.queryString.split("\\s".toRegex()).fold(true, { prev, q ->
|
||||
prev && (it.keywords?.any { it.contains(q, true) } ?: false)
|
||||
})
|
||||
} ?: emptyList()
|
||||
|
|
|
@ -19,7 +19,6 @@ package im.vector.riotx.features.roomdirectory
|
|||
import android.os.Bundle
|
||||
import android.view.MenuItem
|
||||
import android.view.View
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import com.airbnb.epoxy.EpoxyVisibilityTracker
|
||||
import com.airbnb.mvrx.activityViewModel
|
||||
|
@ -47,7 +46,7 @@ class PublicRoomsFragment @Inject constructor(
|
|||
) : VectorBaseFragment(), PublicRoomsController.Callback {
|
||||
|
||||
private val viewModel: RoomDirectoryViewModel by activityViewModel()
|
||||
private lateinit var navigationViewModel: RoomDirectoryNavigationViewModel
|
||||
private lateinit var sharedActionViewModel: RoomDirectorySharedActionViewModel
|
||||
|
||||
override fun getLayoutResId() = R.layout.fragment_public_rooms
|
||||
|
||||
|
@ -66,12 +65,12 @@ class PublicRoomsFragment @Inject constructor(
|
|||
publicRoomsFilter.queryTextChanges()
|
||||
.debounce(500, TimeUnit.MILLISECONDS)
|
||||
.subscribeBy {
|
||||
viewModel.filterWith(it.toString())
|
||||
viewModel.handle(RoomDirectoryAction.FilterWith(it.toString()))
|
||||
}
|
||||
.disposeOnDestroy()
|
||||
|
||||
publicRoomsCreateNewRoom.setOnClickListener {
|
||||
navigationViewModel.post(RoomDirectoryActivity.Navigation.CreateRoom)
|
||||
sharedActionViewModel.post(RoomDirectorySharedAction.CreateRoom)
|
||||
}
|
||||
|
||||
viewModel.joinRoomErrorLiveData.observeEvent(this) { throwable ->
|
||||
|
@ -83,7 +82,7 @@ class PublicRoomsFragment @Inject constructor(
|
|||
override fun onOptionsItemSelected(item: MenuItem): Boolean {
|
||||
return when (item.itemId) {
|
||||
R.id.menu_room_directory_change_protocol -> {
|
||||
navigationViewModel.post(RoomDirectoryActivity.Navigation.ChangeProtocol)
|
||||
sharedActionViewModel.post(RoomDirectorySharedAction.ChangeProtocol)
|
||||
true
|
||||
}
|
||||
else ->
|
||||
|
@ -93,7 +92,7 @@ class PublicRoomsFragment @Inject constructor(
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
navigationViewModel = ViewModelProviders.of(requireActivity()).get(RoomDirectoryNavigationViewModel::class.java)
|
||||
sharedActionViewModel = activityViewModelProvider.get(RoomDirectorySharedActionViewModel::class.java)
|
||||
setupRecyclerView()
|
||||
}
|
||||
|
||||
|
@ -130,14 +129,14 @@ class PublicRoomsFragment @Inject constructor(
|
|||
|
||||
override fun onPublicRoomJoin(publicRoom: PublicRoom) {
|
||||
Timber.v("PublicRoomJoinClicked: $publicRoom")
|
||||
viewModel.joinRoom(publicRoom)
|
||||
viewModel.handle(RoomDirectoryAction.JoinRoom(publicRoom.roomId))
|
||||
}
|
||||
|
||||
override fun loadMore() {
|
||||
viewModel.loadMore()
|
||||
viewModel.handle(RoomDirectoryAction.LoadMore)
|
||||
}
|
||||
|
||||
var initialValueSet = false
|
||||
private var initialValueSet = false
|
||||
|
||||
override fun invalidate() = withState(viewModel) { state ->
|
||||
if (!initialValueSet) {
|
||||
|
|
|
@ -0,0 +1,27 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.roomdirectory
|
||||
|
||||
import im.vector.matrix.android.api.session.room.model.thirdparty.RoomDirectoryData
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class RoomDirectoryAction : VectorViewModelAction {
|
||||
data class SetRoomDirectoryData(val roomDirectoryData: RoomDirectoryData) : RoomDirectoryAction()
|
||||
data class FilterWith(val filter: String) : RoomDirectoryAction()
|
||||
object LoadMore : RoomDirectoryAction()
|
||||
data class JoinRoom(val roomId: String) : RoomDirectoryAction()
|
||||
}
|
|
@ -19,13 +19,13 @@ package im.vector.riotx.features.roomdirectory
|
|||
import android.content.Context
|
||||
import android.content.Intent
|
||||
import android.os.Bundle
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import com.airbnb.mvrx.viewModel
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.di.ScreenComponent
|
||||
import im.vector.riotx.core.extensions.addFragment
|
||||
import im.vector.riotx.core.extensions.addFragmentToBackstack
|
||||
import im.vector.riotx.core.platform.VectorBaseActivity
|
||||
import im.vector.riotx.features.roomdirectory.createroom.CreateRoomAction
|
||||
import im.vector.riotx.features.roomdirectory.createroom.CreateRoomFragment
|
||||
import im.vector.riotx.features.roomdirectory.createroom.CreateRoomViewModel
|
||||
import im.vector.riotx.features.roomdirectory.picker.RoomDirectoryPickerFragment
|
||||
|
@ -33,19 +33,11 @@ import javax.inject.Inject
|
|||
|
||||
class RoomDirectoryActivity : VectorBaseActivity() {
|
||||
|
||||
// Supported navigation actions for this Activity
|
||||
sealed class Navigation {
|
||||
object Back : Navigation()
|
||||
object CreateRoom : Navigation()
|
||||
object Close : Navigation()
|
||||
object ChangeProtocol : Navigation()
|
||||
}
|
||||
|
||||
@Inject lateinit var createRoomViewModelFactory: CreateRoomViewModel.Factory
|
||||
@Inject lateinit var roomDirectoryViewModelFactory: RoomDirectoryViewModel.Factory
|
||||
private val roomDirectoryViewModel: RoomDirectoryViewModel by viewModel()
|
||||
private val createRoomViewModel: CreateRoomViewModel by viewModel()
|
||||
private lateinit var navigationViewModel: RoomDirectoryNavigationViewModel
|
||||
private lateinit var sharedActionViewModel: RoomDirectorySharedActionViewModel
|
||||
|
||||
override fun getLayoutRes() = R.layout.activity_simple
|
||||
|
||||
|
@ -55,26 +47,29 @@ class RoomDirectoryActivity : VectorBaseActivity() {
|
|||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
navigationViewModel = ViewModelProviders.of(this, viewModelFactory).get(RoomDirectoryNavigationViewModel::class.java)
|
||||
sharedActionViewModel = viewModelProvider.get(RoomDirectorySharedActionViewModel::class.java)
|
||||
|
||||
if (isFirstCreation()) {
|
||||
roomDirectoryViewModel.filterWith(intent?.getStringExtra(INITIAL_FILTER) ?: "")
|
||||
roomDirectoryViewModel.handle(RoomDirectoryAction.FilterWith(intent?.getStringExtra(INITIAL_FILTER) ?: ""))
|
||||
}
|
||||
|
||||
navigationViewModel.observe()
|
||||
.subscribe { navigation ->
|
||||
when (navigation) {
|
||||
is Navigation.Back -> onBackPressed()
|
||||
is Navigation.CreateRoom -> addFragmentToBackstack(R.id.simpleFragmentContainer, CreateRoomFragment::class.java)
|
||||
is Navigation.ChangeProtocol -> addFragmentToBackstack(R.id.simpleFragmentContainer, RoomDirectoryPickerFragment::class.java)
|
||||
is Navigation.Close -> finish()
|
||||
sharedActionViewModel
|
||||
.observe()
|
||||
.subscribe { sharedAction ->
|
||||
when (sharedAction) {
|
||||
is RoomDirectorySharedAction.Back -> onBackPressed()
|
||||
is RoomDirectorySharedAction.CreateRoom ->
|
||||
addFragmentToBackstack(R.id.simpleFragmentContainer, CreateRoomFragment::class.java)
|
||||
is RoomDirectorySharedAction.ChangeProtocol ->
|
||||
addFragmentToBackstack(R.id.simpleFragmentContainer, RoomDirectoryPickerFragment::class.java)
|
||||
is RoomDirectorySharedAction.Close -> finish()
|
||||
}
|
||||
}
|
||||
.disposeOnDestroy()
|
||||
|
||||
roomDirectoryViewModel.selectSubscribe(this, PublicRoomsViewState::currentFilter) { currentFilter ->
|
||||
// Transmit the filter to the createRoomViewModel
|
||||
createRoomViewModel.setName(currentFilter)
|
||||
createRoomViewModel.handle(CreateRoomAction.SetName(currentFilter))
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,29 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.roomdirectory
|
||||
|
||||
import im.vector.riotx.core.platform.VectorSharedAction
|
||||
|
||||
/**
|
||||
* Supported navigation actions for [RoomDirectoryActivity]
|
||||
*/
|
||||
sealed class RoomDirectorySharedAction : VectorSharedAction {
|
||||
object Back : RoomDirectorySharedAction()
|
||||
object CreateRoom : RoomDirectorySharedAction()
|
||||
object Close : RoomDirectorySharedAction()
|
||||
object ChangeProtocol : RoomDirectorySharedAction()
|
||||
}
|
|
@ -16,9 +16,7 @@
|
|||
|
||||
package im.vector.riotx.features.roomdirectory
|
||||
|
||||
import androidx.lifecycle.ViewModel
|
||||
import im.vector.riotx.core.utils.PublishDataSource
|
||||
import im.vector.riotx.core.utils.MutableDataSource
|
||||
import im.vector.riotx.core.platform.VectorSharedActionViewModel
|
||||
import javax.inject.Inject
|
||||
|
||||
class RoomDirectoryNavigationViewModel(private val source: MutableDataSource<RoomDirectoryActivity.Navigation> = PublishDataSource())
|
||||
: ViewModel(), MutableDataSource<RoomDirectoryActivity.Navigation> by source
|
||||
class RoomDirectorySharedActionViewModel @Inject constructor() : VectorSharedActionViewModel<RoomDirectorySharedAction>()
|
|
@ -25,7 +25,6 @@ import im.vector.matrix.android.api.MatrixCallback
|
|||
import im.vector.matrix.android.api.failure.Failure
|
||||
import im.vector.matrix.android.api.session.Session
|
||||
import im.vector.matrix.android.api.session.room.model.Membership
|
||||
import im.vector.matrix.android.api.session.room.model.roomdirectory.PublicRoom
|
||||
import im.vector.matrix.android.api.session.room.model.roomdirectory.PublicRoomsFilter
|
||||
import im.vector.matrix.android.api.session.room.model.roomdirectory.PublicRoomsParams
|
||||
import im.vector.matrix.android.api.session.room.model.roomdirectory.PublicRoomsResponse
|
||||
|
@ -40,7 +39,8 @@ import timber.log.Timber
|
|||
private const val PUBLIC_ROOMS_LIMIT = 20
|
||||
|
||||
class RoomDirectoryViewModel @AssistedInject constructor(@Assisted initialState: PublicRoomsViewState,
|
||||
private val session: Session) : VectorViewModel<PublicRoomsViewState>(initialState) {
|
||||
private val session: Session)
|
||||
: VectorViewModel<PublicRoomsViewState, RoomDirectoryAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -103,23 +103,32 @@ class RoomDirectoryViewModel @AssistedInject constructor(@Assisted initialState:
|
|||
.disposeOnClear()
|
||||
}
|
||||
|
||||
fun setRoomDirectoryData(roomDirectoryData: RoomDirectoryData) {
|
||||
if (this.roomDirectoryData == roomDirectoryData) {
|
||||
override fun handle(action: RoomDirectoryAction) {
|
||||
when (action) {
|
||||
is RoomDirectoryAction.SetRoomDirectoryData -> setRoomDirectoryData(action)
|
||||
is RoomDirectoryAction.FilterWith -> filterWith(action)
|
||||
RoomDirectoryAction.LoadMore -> loadMore()
|
||||
is RoomDirectoryAction.JoinRoom -> joinRoom(action)
|
||||
}
|
||||
}
|
||||
|
||||
private fun setRoomDirectoryData(action: RoomDirectoryAction.SetRoomDirectoryData) {
|
||||
if (this.roomDirectoryData == action.roomDirectoryData) {
|
||||
return
|
||||
}
|
||||
|
||||
this.roomDirectoryData = roomDirectoryData
|
||||
this.roomDirectoryData = action.roomDirectoryData
|
||||
|
||||
reset("")
|
||||
load("")
|
||||
}
|
||||
|
||||
fun filterWith(filter: String) = withState { state ->
|
||||
if (state.currentFilter != filter) {
|
||||
private fun filterWith(action: RoomDirectoryAction.FilterWith) = withState { state ->
|
||||
if (state.currentFilter != action.filter) {
|
||||
currentTask?.cancel()
|
||||
|
||||
reset(filter)
|
||||
load(filter)
|
||||
reset(action.filter)
|
||||
load(action.filter)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -138,7 +147,7 @@ class RoomDirectoryViewModel @AssistedInject constructor(@Assisted initialState:
|
|||
}
|
||||
}
|
||||
|
||||
fun loadMore() = withState { state ->
|
||||
private fun loadMore() = withState { state ->
|
||||
if (currentTask == null) {
|
||||
setState {
|
||||
copy(
|
||||
|
@ -192,8 +201,8 @@ class RoomDirectoryViewModel @AssistedInject constructor(@Assisted initialState:
|
|||
})
|
||||
}
|
||||
|
||||
fun joinRoom(publicRoom: PublicRoom) = withState { state ->
|
||||
if (state.joiningRoomsIds.contains(publicRoom.roomId)) {
|
||||
private fun joinRoom(action: RoomDirectoryAction.JoinRoom) = withState { state ->
|
||||
if (state.joiningRoomsIds.contains(action.roomId)) {
|
||||
// Request already sent, should not happen
|
||||
Timber.w("Try to join an already joining room. Should not happen")
|
||||
return@withState
|
||||
|
@ -201,11 +210,11 @@ class RoomDirectoryViewModel @AssistedInject constructor(@Assisted initialState:
|
|||
|
||||
setState {
|
||||
copy(
|
||||
joiningRoomsIds = joiningRoomsIds.toMutableSet().apply { add(publicRoom.roomId) }
|
||||
joiningRoomsIds = joiningRoomsIds.toMutableSet().apply { add(action.roomId) }
|
||||
)
|
||||
}
|
||||
|
||||
session.joinRoom(publicRoom.roomId, emptyList(), object : MatrixCallback<Unit> {
|
||||
session.joinRoom(action.roomId, emptyList(), object : MatrixCallback<Unit> {
|
||||
override fun onSuccess(data: Unit) {
|
||||
// We do not update the joiningRoomsIds here, because, the room is not joined yet regarding the sync data.
|
||||
// Instead, we wait for the room to be joined
|
||||
|
@ -217,8 +226,8 @@ class RoomDirectoryViewModel @AssistedInject constructor(@Assisted initialState:
|
|||
|
||||
setState {
|
||||
copy(
|
||||
joiningRoomsIds = joiningRoomsIds.toMutableSet().apply { remove(publicRoom.roomId) },
|
||||
joiningErrorRoomsIds = joiningErrorRoomsIds.toMutableSet().apply { add(publicRoom.roomId) }
|
||||
joiningRoomsIds = joiningRoomsIds.toMutableSet().apply { remove(action.roomId) },
|
||||
joiningErrorRoomsIds = joiningErrorRoomsIds.toMutableSet().apply { add(action.roomId) }
|
||||
)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,26 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.roomdirectory.createroom
|
||||
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class CreateRoomAction : VectorViewModelAction {
|
||||
data class SetName(val name: String) : CreateRoomAction()
|
||||
data class SetIsPublic(val isPublic: Boolean) : CreateRoomAction()
|
||||
data class SetIsInRoomDirectory(val isInRoomDirectory: Boolean) : CreateRoomAction()
|
||||
object Create : CreateRoomAction()
|
||||
}
|
|
@ -20,14 +20,13 @@ import android.content.Context
|
|||
import android.content.Intent
|
||||
import android.os.Bundle
|
||||
import androidx.appcompat.widget.Toolbar
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import com.airbnb.mvrx.viewModel
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.extensions.addFragment
|
||||
import im.vector.riotx.core.platform.ToolbarConfigurable
|
||||
import im.vector.riotx.core.platform.VectorBaseActivity
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectoryActivity
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectoryNavigationViewModel
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectorySharedAction
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectorySharedActionViewModel
|
||||
import javax.inject.Inject
|
||||
|
||||
/**
|
||||
|
@ -38,7 +37,7 @@ class CreateRoomActivity : VectorBaseActivity(), ToolbarConfigurable {
|
|||
@Inject lateinit var createRoomViewModelFactory: CreateRoomViewModel.Factory
|
||||
private val createRoomViewModel: CreateRoomViewModel by viewModel()
|
||||
|
||||
private lateinit var navigationViewModel: RoomDirectoryNavigationViewModel
|
||||
private lateinit var sharedActionViewModel: RoomDirectorySharedActionViewModel
|
||||
|
||||
override fun getLayoutRes() = R.layout.activity_simple
|
||||
|
||||
|
@ -49,18 +48,19 @@ class CreateRoomActivity : VectorBaseActivity(), ToolbarConfigurable {
|
|||
override fun initUiAndData() {
|
||||
if (isFirstCreation()) {
|
||||
addFragment(R.id.simpleFragmentContainer, CreateRoomFragment::class.java)
|
||||
createRoomViewModel.setName(intent?.getStringExtra(INITIAL_NAME) ?: "")
|
||||
createRoomViewModel.handle(CreateRoomAction.SetName(intent?.getStringExtra(INITIAL_NAME) ?: ""))
|
||||
}
|
||||
}
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
navigationViewModel = ViewModelProviders.of(this, viewModelFactory).get(RoomDirectoryNavigationViewModel::class.java)
|
||||
navigationViewModel.observe()
|
||||
.subscribe { navigation ->
|
||||
when (navigation) {
|
||||
is RoomDirectoryActivity.Navigation.Back,
|
||||
is RoomDirectoryActivity.Navigation.Close -> finish()
|
||||
sharedActionViewModel = viewModelProvider.get(RoomDirectorySharedActionViewModel::class.java)
|
||||
sharedActionViewModel
|
||||
.observe()
|
||||
.subscribe { sharedAction ->
|
||||
when (sharedAction) {
|
||||
is RoomDirectorySharedAction.Back,
|
||||
is RoomDirectorySharedAction.Close -> finish()
|
||||
}
|
||||
}
|
||||
.disposeOnDestroy()
|
||||
|
|
|
@ -18,22 +18,21 @@ package im.vector.riotx.features.roomdirectory.createroom
|
|||
|
||||
import android.os.Bundle
|
||||
import android.view.MenuItem
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import com.airbnb.mvrx.Success
|
||||
import com.airbnb.mvrx.activityViewModel
|
||||
import com.airbnb.mvrx.withState
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.platform.VectorBaseFragment
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectoryActivity
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectoryNavigationViewModel
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectorySharedAction
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectorySharedActionViewModel
|
||||
import kotlinx.android.synthetic.main.fragment_create_room.*
|
||||
import timber.log.Timber
|
||||
import javax.inject.Inject
|
||||
|
||||
class CreateRoomFragment @Inject constructor(private val createRoomController: CreateRoomController): VectorBaseFragment(), CreateRoomController.Listener {
|
||||
class CreateRoomFragment @Inject constructor(private val createRoomController: CreateRoomController) : VectorBaseFragment(), CreateRoomController.Listener {
|
||||
|
||||
private lateinit var navigationViewModel: RoomDirectoryNavigationViewModel
|
||||
private lateinit var sharedActionViewModel: RoomDirectorySharedActionViewModel
|
||||
private val viewModel: CreateRoomViewModel by activityViewModel()
|
||||
|
||||
override fun getLayoutResId() = R.layout.fragment_create_room
|
||||
|
@ -43,17 +42,17 @@ class CreateRoomFragment @Inject constructor(private val createRoomController: C
|
|||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
vectorBaseActivity.setSupportActionBar(createRoomToolbar)
|
||||
navigationViewModel = ViewModelProviders.of(requireActivity()).get(RoomDirectoryNavigationViewModel::class.java)
|
||||
sharedActionViewModel = activityViewModelProvider.get(RoomDirectorySharedActionViewModel::class.java)
|
||||
setupRecyclerView()
|
||||
createRoomClose.setOnClickListener {
|
||||
navigationViewModel.post(RoomDirectoryActivity.Navigation.Back)
|
||||
sharedActionViewModel.post(RoomDirectorySharedAction.Back)
|
||||
}
|
||||
}
|
||||
|
||||
override fun onOptionsItemSelected(item: MenuItem): Boolean {
|
||||
return when (item.itemId) {
|
||||
R.id.action_create_room -> {
|
||||
viewModel.doCreateRoom()
|
||||
viewModel.handle(CreateRoomAction.Create)
|
||||
true
|
||||
}
|
||||
else ->
|
||||
|
@ -71,20 +70,20 @@ class CreateRoomFragment @Inject constructor(private val createRoomController: C
|
|||
}
|
||||
|
||||
override fun onNameChange(newName: String) {
|
||||
viewModel.setName(newName)
|
||||
viewModel.handle(CreateRoomAction.SetName(newName))
|
||||
}
|
||||
|
||||
override fun setIsPublic(isPublic: Boolean) {
|
||||
viewModel.setIsPublic(isPublic)
|
||||
viewModel.handle(CreateRoomAction.SetIsPublic(isPublic))
|
||||
}
|
||||
|
||||
override fun setIsInRoomDirectory(isInRoomDirectory: Boolean) {
|
||||
viewModel.setIsInRoomDirectory(isInRoomDirectory)
|
||||
viewModel.handle(CreateRoomAction.SetIsInRoomDirectory(isInRoomDirectory))
|
||||
}
|
||||
|
||||
override fun retry() {
|
||||
Timber.v("Retry")
|
||||
viewModel.doCreateRoom()
|
||||
viewModel.handle(CreateRoomAction.Create)
|
||||
}
|
||||
|
||||
override fun invalidate() = withState(viewModel) { state ->
|
||||
|
@ -93,7 +92,7 @@ class CreateRoomFragment @Inject constructor(private val createRoomController: C
|
|||
// Navigate to freshly created room
|
||||
navigator.openRoom(requireActivity(), async())
|
||||
|
||||
navigationViewModel.post(RoomDirectoryActivity.Navigation.Close)
|
||||
sharedActionViewModel.post(RoomDirectorySharedAction.Close)
|
||||
} else {
|
||||
// Populate list with Epoxy
|
||||
createRoomController.setData(state)
|
||||
|
|
|
@ -30,7 +30,7 @@ import im.vector.riotx.features.roomdirectory.RoomDirectoryActivity
|
|||
|
||||
class CreateRoomViewModel @AssistedInject constructor(@Assisted initialState: CreateRoomViewState,
|
||||
private val session: Session
|
||||
) : VectorViewModel<CreateRoomViewState>(initialState) {
|
||||
) : VectorViewModel<CreateRoomViewState, CreateRoomAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -46,18 +46,27 @@ class CreateRoomViewModel @AssistedInject constructor(@Assisted initialState: Cr
|
|||
return when (activity) {
|
||||
is CreateRoomActivity -> activity.createRoomViewModelFactory.create(state)
|
||||
is RoomDirectoryActivity -> activity.createRoomViewModelFactory.create(state)
|
||||
else -> throw IllegalStateException("Wrong activity")
|
||||
else -> error("Wrong activity")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun setName(newName: String) = setState { copy(roomName = newName) }
|
||||
override fun handle(action: CreateRoomAction) {
|
||||
when (action) {
|
||||
is CreateRoomAction.SetName -> setName(action)
|
||||
is CreateRoomAction.SetIsPublic -> setIsPublic(action)
|
||||
is CreateRoomAction.SetIsInRoomDirectory -> setIsInRoomDirectory(action)
|
||||
is CreateRoomAction.Create -> doCreateRoom()
|
||||
}
|
||||
}
|
||||
|
||||
fun setIsPublic(isPublic: Boolean) = setState { copy(isPublic = isPublic) }
|
||||
private fun setName(action: CreateRoomAction.SetName) = setState { copy(roomName = action.name) }
|
||||
|
||||
fun setIsInRoomDirectory(isInRoomDirectory: Boolean) = setState { copy(isInRoomDirectory = isInRoomDirectory) }
|
||||
private fun setIsPublic(action: CreateRoomAction.SetIsPublic) = setState { copy(isPublic = action.isPublic) }
|
||||
|
||||
fun doCreateRoom() = withState { state ->
|
||||
private fun setIsInRoomDirectory(action: CreateRoomAction.SetIsInRoomDirectory) = setState { copy(isInRoomDirectory = action.isInRoomDirectory) }
|
||||
|
||||
private fun doCreateRoom() = withState { state ->
|
||||
if (state.asyncCreateRoomRequest is Loading || state.asyncCreateRoomRequest is Success) {
|
||||
return@withState
|
||||
}
|
||||
|
|
|
@ -0,0 +1,23 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.roomdirectory.picker
|
||||
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class RoomDirectoryPickerAction : VectorViewModelAction {
|
||||
object Retry : RoomDirectoryPickerAction()
|
||||
}
|
|
@ -19,7 +19,6 @@ package im.vector.riotx.features.roomdirectory.picker
|
|||
import android.os.Bundle
|
||||
import android.view.MenuItem
|
||||
import android.view.View
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import com.airbnb.mvrx.activityViewModel
|
||||
import com.airbnb.mvrx.fragmentViewModel
|
||||
|
@ -27,8 +26,9 @@ import com.airbnb.mvrx.withState
|
|||
import im.vector.matrix.android.api.session.room.model.thirdparty.RoomDirectoryData
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.platform.VectorBaseFragment
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectoryActivity
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectoryNavigationViewModel
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectoryAction
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectorySharedAction
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectorySharedActionViewModel
|
||||
import im.vector.riotx.features.roomdirectory.RoomDirectoryViewModel
|
||||
import kotlinx.android.synthetic.main.fragment_room_directory_picker.*
|
||||
import timber.log.Timber
|
||||
|
@ -41,7 +41,7 @@ class RoomDirectoryPickerFragment @Inject constructor(val roomDirectoryPickerVie
|
|||
) : VectorBaseFragment(), RoomDirectoryPickerController.Callback {
|
||||
|
||||
private val viewModel: RoomDirectoryViewModel by activityViewModel()
|
||||
private lateinit var navigationViewModel: RoomDirectoryNavigationViewModel
|
||||
private lateinit var sharedActionViewModel: RoomDirectorySharedActionViewModel
|
||||
private val pickerViewModel: RoomDirectoryPickerViewModel by fragmentViewModel()
|
||||
|
||||
override fun getLayoutResId() = R.layout.fragment_room_directory_picker
|
||||
|
@ -71,7 +71,7 @@ class RoomDirectoryPickerFragment @Inject constructor(val roomDirectoryPickerVie
|
|||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
navigationViewModel = ViewModelProviders.of(requireActivity()).get(RoomDirectoryNavigationViewModel::class.java)
|
||||
sharedActionViewModel = activityViewModelProvider.get(RoomDirectorySharedActionViewModel::class.java)
|
||||
setupRecyclerView()
|
||||
}
|
||||
|
||||
|
@ -86,14 +86,14 @@ class RoomDirectoryPickerFragment @Inject constructor(val roomDirectoryPickerVie
|
|||
|
||||
override fun onRoomDirectoryClicked(roomDirectoryData: RoomDirectoryData) {
|
||||
Timber.v("onRoomDirectoryClicked: $roomDirectoryData")
|
||||
viewModel.setRoomDirectoryData(roomDirectoryData)
|
||||
viewModel.handle(RoomDirectoryAction.SetRoomDirectoryData(roomDirectoryData))
|
||||
|
||||
navigationViewModel.post(RoomDirectoryActivity.Navigation.Back)
|
||||
sharedActionViewModel.post(RoomDirectorySharedAction.Back)
|
||||
}
|
||||
|
||||
override fun retry() {
|
||||
Timber.v("Retry")
|
||||
pickerViewModel.load()
|
||||
pickerViewModel.handle(RoomDirectoryPickerAction.Retry)
|
||||
}
|
||||
|
||||
override fun invalidate() = withState(pickerViewModel) { state ->
|
||||
|
|
|
@ -16,11 +16,7 @@
|
|||
|
||||
package im.vector.riotx.features.roomdirectory.picker
|
||||
|
||||
import com.airbnb.mvrx.Fail
|
||||
import com.airbnb.mvrx.FragmentViewModelContext
|
||||
import com.airbnb.mvrx.MvRxViewModelFactory
|
||||
import com.airbnb.mvrx.Success
|
||||
import com.airbnb.mvrx.ViewModelContext
|
||||
import com.airbnb.mvrx.*
|
||||
import com.squareup.inject.assisted.Assisted
|
||||
import com.squareup.inject.assisted.AssistedInject
|
||||
import im.vector.matrix.android.api.MatrixCallback
|
||||
|
@ -29,7 +25,8 @@ import im.vector.matrix.android.api.session.room.model.thirdparty.ThirdPartyProt
|
|||
import im.vector.riotx.core.platform.VectorViewModel
|
||||
|
||||
class RoomDirectoryPickerViewModel @AssistedInject constructor(@Assisted initialState: RoomDirectoryPickerViewState,
|
||||
private val session: Session) : VectorViewModel<RoomDirectoryPickerViewState>(initialState) {
|
||||
private val session: Session)
|
||||
: VectorViewModel<RoomDirectoryPickerViewState, RoomDirectoryPickerAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -49,7 +46,7 @@ class RoomDirectoryPickerViewModel @AssistedInject constructor(@Assisted initial
|
|||
load()
|
||||
}
|
||||
|
||||
fun load() {
|
||||
private fun load() {
|
||||
session.getThirdPartyProtocol(object : MatrixCallback<Map<String, ThirdPartyProtocol>> {
|
||||
override fun onSuccess(data: Map<String, ThirdPartyProtocol>) {
|
||||
setState {
|
||||
|
@ -64,4 +61,10 @@ class RoomDirectoryPickerViewModel @AssistedInject constructor(@Assisted initial
|
|||
}
|
||||
})
|
||||
}
|
||||
|
||||
override fun handle(action: RoomDirectoryPickerAction) {
|
||||
when (action) {
|
||||
RoomDirectoryPickerAction.Retry -> load()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,23 @@
|
|||
/*
|
||||
* Copyright 2019 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package im.vector.riotx.features.roomdirectory.roompreview
|
||||
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
sealed class RoomPreviewAction : VectorViewModelAction {
|
||||
object Join : RoomPreviewAction()
|
||||
}
|
|
@ -72,7 +72,7 @@ class RoomPreviewNoPreviewFragment @Inject constructor(
|
|||
|
||||
roomPreviewNoPreviewJoin.callback = object : ButtonStateView.Callback {
|
||||
override fun onButtonClicked() {
|
||||
roomPreviewViewModel.joinRoom()
|
||||
roomPreviewViewModel.handle(RoomPreviewAction.Join)
|
||||
}
|
||||
|
||||
override fun onRetryClicked() {
|
||||
|
|
|
@ -30,7 +30,8 @@ import im.vector.riotx.features.roomdirectory.JoinState
|
|||
import timber.log.Timber
|
||||
|
||||
class RoomPreviewViewModel @AssistedInject constructor(@Assisted initialState: RoomPreviewViewState,
|
||||
private val session: Session) : VectorViewModel<RoomPreviewViewState>(initialState) {
|
||||
private val session: Session)
|
||||
: VectorViewModel<RoomPreviewViewState, RoomPreviewAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -76,7 +77,13 @@ class RoomPreviewViewModel @AssistedInject constructor(@Assisted initialState: R
|
|||
.disposeOnClear()
|
||||
}
|
||||
|
||||
fun joinRoom() = withState { state ->
|
||||
override fun handle(action: RoomPreviewAction) {
|
||||
when (action) {
|
||||
RoomPreviewAction.Join -> joinRoom()
|
||||
}
|
||||
}
|
||||
|
||||
private fun joinRoom() = withState { state ->
|
||||
if (state.roomJoinState == JoinState.JOINING) {
|
||||
// Request already sent, should not happen
|
||||
Timber.w("Try to join an already joining room. Should not happen")
|
||||
|
|
|
@ -25,18 +25,20 @@ import im.vector.matrix.android.api.session.user.model.User
|
|||
import im.vector.matrix.rx.rx
|
||||
import im.vector.riotx.core.extensions.postLiveEvent
|
||||
import im.vector.riotx.core.platform.VectorViewModel
|
||||
import im.vector.riotx.core.platform.VectorViewModelAction
|
||||
|
||||
data class IgnoredUsersViewState(
|
||||
val ignoredUsers: List<User> = emptyList(),
|
||||
val unIgnoreRequest: Async<Unit> = Uninitialized
|
||||
) : MvRxState
|
||||
|
||||
sealed class IgnoredUsersAction {
|
||||
sealed class IgnoredUsersAction : VectorViewModelAction {
|
||||
data class UnIgnore(val userId: String) : IgnoredUsersAction()
|
||||
}
|
||||
|
||||
class IgnoredUsersViewModel @AssistedInject constructor(@Assisted initialState: IgnoredUsersViewState,
|
||||
private val session: Session) : VectorViewModel<IgnoredUsersViewState>(initialState) {
|
||||
private val session: Session)
|
||||
: VectorViewModel<IgnoredUsersViewState, IgnoredUsersAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -66,7 +68,7 @@ class IgnoredUsersViewModel @AssistedInject constructor(@Assisted initialState:
|
|||
}
|
||||
}
|
||||
|
||||
fun handle(action: IgnoredUsersAction) {
|
||||
override fun handle(action: IgnoredUsersAction) {
|
||||
when (action) {
|
||||
is IgnoredUsersAction.UnIgnore -> handleUnIgnore(action)
|
||||
}
|
||||
|
|
|
@ -16,17 +16,13 @@
|
|||
|
||||
package im.vector.riotx.features.settings.push
|
||||
|
||||
import com.airbnb.mvrx.Async
|
||||
import com.airbnb.mvrx.FragmentViewModelContext
|
||||
import com.airbnb.mvrx.MvRxState
|
||||
import com.airbnb.mvrx.MvRxViewModelFactory
|
||||
import com.airbnb.mvrx.Uninitialized
|
||||
import com.airbnb.mvrx.ViewModelContext
|
||||
import com.airbnb.mvrx.*
|
||||
import com.squareup.inject.assisted.Assisted
|
||||
import com.squareup.inject.assisted.AssistedInject
|
||||
import im.vector.matrix.android.api.session.Session
|
||||
import im.vector.matrix.android.api.session.pushers.Pusher
|
||||
import im.vector.matrix.rx.RxSession
|
||||
import im.vector.riotx.core.platform.EmptyAction
|
||||
import im.vector.riotx.core.platform.VectorViewModel
|
||||
|
||||
data class PushGatewayViewState(
|
||||
|
@ -34,7 +30,8 @@ data class PushGatewayViewState(
|
|||
) : MvRxState
|
||||
|
||||
class PushGatewaysViewModel @AssistedInject constructor(@Assisted initialState: PushGatewayViewState,
|
||||
private val session: Session) : VectorViewModel<PushGatewayViewState>(initialState) {
|
||||
private val session: Session)
|
||||
: VectorViewModel<PushGatewayViewState, EmptyAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -60,4 +57,8 @@ class PushGatewaysViewModel @AssistedInject constructor(@Assisted initialState:
|
|||
copy(pushGateways = it)
|
||||
}
|
||||
}
|
||||
|
||||
override fun handle(action: EmptyAction) {
|
||||
// No op
|
||||
}
|
||||
}
|
||||
|
|
|
@ -20,13 +20,15 @@ import com.airbnb.mvrx.MvRxViewModelFactory
|
|||
import com.airbnb.mvrx.ViewModelContext
|
||||
import im.vector.matrix.android.api.pushrules.rest.PushRule
|
||||
import im.vector.riotx.core.di.HasScreenInjector
|
||||
import im.vector.riotx.core.platform.EmptyAction
|
||||
import im.vector.riotx.core.platform.VectorViewModel
|
||||
|
||||
data class PushRulesViewState(
|
||||
val rules: List<PushRule> = emptyList()
|
||||
) : MvRxState
|
||||
|
||||
class PushRulesViewModel(initialState: PushRulesViewState) : VectorViewModel<PushRulesViewState>(initialState) {
|
||||
class PushRulesViewModel(initialState: PushRulesViewState)
|
||||
: VectorViewModel<PushRulesViewState, EmptyAction>(initialState) {
|
||||
|
||||
companion object : MvRxViewModelFactory<PushRulesViewModel, PushRulesViewState> {
|
||||
|
||||
|
@ -36,4 +38,8 @@ class PushRulesViewModel(initialState: PushRulesViewState) : VectorViewModel<Pus
|
|||
return PushRulesViewState(rules)
|
||||
}
|
||||
}
|
||||
|
||||
override fun handle(action: EmptyAction) {
|
||||
// No op
|
||||
}
|
||||
}
|
||||
|
|
|
@ -24,6 +24,7 @@ import com.squareup.inject.assisted.Assisted
|
|||
import com.squareup.inject.assisted.AssistedInject
|
||||
import im.vector.matrix.rx.rx
|
||||
import im.vector.riotx.ActiveSessionDataSource
|
||||
import im.vector.riotx.core.platform.EmptyAction
|
||||
import im.vector.riotx.core.platform.VectorViewModel
|
||||
import io.reactivex.Observable
|
||||
import io.reactivex.android.schedulers.AndroidSchedulers
|
||||
|
@ -37,7 +38,7 @@ data class IncomingShareState(private val dummy: Boolean = false) : MvRxState
|
|||
class IncomingShareViewModel @AssistedInject constructor(@Assisted initialState: IncomingShareState,
|
||||
private val sessionObservableStore: ActiveSessionDataSource,
|
||||
private val shareRoomListObservableStore: ShareRoomListDataSource)
|
||||
: VectorViewModel<IncomingShareState>(initialState) {
|
||||
: VectorViewModel<IncomingShareState, EmptyAction>(initialState) {
|
||||
|
||||
@AssistedInject.Factory
|
||||
interface Factory {
|
||||
|
@ -70,4 +71,8 @@ class IncomingShareViewModel @AssistedInject constructor(@Assisted initialState:
|
|||
}
|
||||
.disposeOnClear()
|
||||
}
|
||||
|
||||
override fun handle(action: EmptyAction) {
|
||||
// No op
|
||||
}
|
||||
}
|
||||
|
|
|
@ -18,7 +18,6 @@ package im.vector.riotx.features.workers.signout
|
|||
|
||||
import android.app.Activity
|
||||
import android.app.Dialog
|
||||
import android.content.Context
|
||||
import android.content.Intent
|
||||
import android.os.Bundle
|
||||
import android.view.LayoutInflater
|
||||
|
@ -31,27 +30,19 @@ import android.widget.TextView
|
|||
import androidx.appcompat.app.AlertDialog
|
||||
import androidx.core.view.isVisible
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.lifecycle.ViewModelProvider
|
||||
import androidx.lifecycle.ViewModelProviders
|
||||
import androidx.transition.TransitionManager
|
||||
import butterknife.BindView
|
||||
import butterknife.ButterKnife
|
||||
import com.google.android.material.bottomsheet.BottomSheetBehavior
|
||||
import com.google.android.material.bottomsheet.BottomSheetDialog
|
||||
import com.google.android.material.bottomsheet.BottomSheetDialogFragment
|
||||
import im.vector.matrix.android.api.session.Session
|
||||
import im.vector.matrix.android.api.session.crypto.keysbackup.KeysBackupState
|
||||
import im.vector.riotx.R
|
||||
import im.vector.riotx.core.di.DaggerScreenComponent
|
||||
import im.vector.riotx.core.platform.VectorBaseActivity
|
||||
import im.vector.riotx.core.platform.VectorBaseBottomSheetDialogFragment
|
||||
import im.vector.riotx.core.utils.toast
|
||||
import im.vector.riotx.features.crypto.keysbackup.settings.KeysBackupManageActivity
|
||||
import im.vector.riotx.features.crypto.keysbackup.setup.KeysBackupSetupActivity
|
||||
|
||||
class SignOutBottomSheetDialogFragment : BottomSheetDialogFragment() {
|
||||
|
||||
lateinit var session: Session
|
||||
lateinit var viewModelFactory: ViewModelProvider.Factory
|
||||
class SignOutBottomSheetDialogFragment : VectorBaseBottomSheetDialogFragment() {
|
||||
|
||||
@BindView(R.id.bottom_sheet_signout_warning_text)
|
||||
lateinit var sheetTitle: TextView
|
||||
|
@ -97,20 +88,10 @@ class SignOutBottomSheetDialogFragment : BottomSheetDialogFragment() {
|
|||
|
||||
private lateinit var viewModel: SignOutViewModel
|
||||
|
||||
override fun onAttach(context: Context) {
|
||||
super.onAttach(context)
|
||||
val vectorBaseActivity = activity as VectorBaseActivity
|
||||
val screenComponent = DaggerScreenComponent.factory().create(vectorBaseActivity.getVectorComponent(), vectorBaseActivity)
|
||||
viewModelFactory = screenComponent.viewModelFactory()
|
||||
session = screenComponent.activeSessionHolder().getActiveSession()
|
||||
}
|
||||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
|
||||
viewModel = ViewModelProviders.of(this, viewModelFactory).get(SignOutViewModel::class.java)
|
||||
|
||||
viewModel.init(session)
|
||||
viewModel = fragmentViewModelProvider.get(SignOutViewModel::class.java)
|
||||
|
||||
setupClickableView.setOnClickListener {
|
||||
context?.let { context ->
|
||||
|
@ -162,7 +143,7 @@ class SignOutBottomSheetDialogFragment : BottomSheetDialogFragment() {
|
|||
}
|
||||
}
|
||||
|
||||
viewModel.keysExportedToFile.observe(this, Observer {
|
||||
viewModel.keysExportedToFile.observe(viewLifecycleOwner, Observer {
|
||||
val hasExportedToFile = it ?: false
|
||||
if (hasExportedToFile) {
|
||||
// We can allow to sign out
|
||||
|
@ -177,7 +158,7 @@ class SignOutBottomSheetDialogFragment : BottomSheetDialogFragment() {
|
|||
}
|
||||
})
|
||||
|
||||
viewModel.keysBackupState.observe(this, Observer {
|
||||
viewModel.keysBackupState.observe(viewLifecycleOwner, Observer {
|
||||
if (viewModel.keysExportedToFile.value == true) {
|
||||
// ignore this
|
||||
return@Observer
|
||||
|
|
|
@ -23,59 +23,43 @@ import im.vector.matrix.android.api.session.crypto.keysbackup.KeysBackupState
|
|||
import im.vector.matrix.android.api.session.crypto.keysbackup.KeysBackupStateListener
|
||||
import javax.inject.Inject
|
||||
|
||||
class SignOutViewModel @Inject constructor() : ViewModel(), KeysBackupStateListener {
|
||||
class SignOutViewModel @Inject constructor(private val session: Session) : ViewModel(), KeysBackupStateListener {
|
||||
// Keys exported manually
|
||||
var keysExportedToFile = MutableLiveData<Boolean>()
|
||||
|
||||
var keysBackupState = MutableLiveData<KeysBackupState>()
|
||||
|
||||
private var mxSession: Session? = null
|
||||
init {
|
||||
session.getKeysBackupService().addListener(this)
|
||||
|
||||
fun init(session: Session) {
|
||||
if (mxSession == null) {
|
||||
mxSession = session
|
||||
|
||||
mxSession?.getKeysBackupService()
|
||||
?.addListener(this)
|
||||
}
|
||||
|
||||
keysBackupState.value = mxSession?.getKeysBackupService()
|
||||
?.state
|
||||
keysBackupState.value = session.getKeysBackupService().state
|
||||
}
|
||||
|
||||
/**
|
||||
* Safe way to get the current KeysBackup version
|
||||
*/
|
||||
fun getCurrentBackupVersion(): String {
|
||||
return mxSession
|
||||
?.getKeysBackupService()
|
||||
?.currentBackupVersion
|
||||
?: ""
|
||||
return session.getKeysBackupService().currentBackupVersion ?: ""
|
||||
}
|
||||
|
||||
/**
|
||||
* Safe way to get the number of keys to backup
|
||||
*/
|
||||
fun getNumberOfKeysToBackup(): Int {
|
||||
return mxSession
|
||||
?.inboundGroupSessionsCount(false)
|
||||
?: 0
|
||||
return session.inboundGroupSessionsCount(false)
|
||||
}
|
||||
|
||||
/**
|
||||
* Safe way to tell if there are more keys on the server
|
||||
*/
|
||||
fun canRestoreKeys(): Boolean {
|
||||
return mxSession
|
||||
?.getKeysBackupService()
|
||||
?.canRestoreKeys() == true
|
||||
return session.getKeysBackupService().canRestoreKeys()
|
||||
}
|
||||
|
||||
override fun onCleared() {
|
||||
super.onCleared()
|
||||
|
||||
mxSession?.getKeysBackupService()
|
||||
?.removeListener(this)
|
||||
session.getKeysBackupService().removeListener(this)
|
||||
}
|
||||
|
||||
override fun onStateChange(newState: KeysBackupState) {
|
||||
|
@ -84,7 +68,7 @@ class SignOutViewModel @Inject constructor() : ViewModel(), KeysBackupStateListe
|
|||
|
||||
fun refreshRemoteStateIfNeeded() {
|
||||
if (keysBackupState.value == KeysBackupState.Disabled) {
|
||||
mxSession?.getKeysBackupService()?.checkAndStartKeysBackup()
|
||||
session.getKeysBackupService().checkAndStartKeysBackup()
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -92,13 +76,9 @@ class SignOutViewModel @Inject constructor() : ViewModel(), KeysBackupStateListe
|
|||
/**
|
||||
* The backup check on logout flow has to be displayed if there are keys in the store, and the keys backup state is not Ready
|
||||
*/
|
||||
fun doYouNeedToBeDisplayed(session: Session?): Boolean {
|
||||
return session
|
||||
?.inboundGroupSessionsCount(false)
|
||||
?: 0 > 0
|
||||
&& session
|
||||
?.getKeysBackupService()
|
||||
?.state != KeysBackupState.ReadyToBackUp
|
||||
fun doYouNeedToBeDisplayed(session: Session): Boolean {
|
||||
return session.inboundGroupSessionsCount(false) > 0
|
||||
&& session.getKeysBackupService().state != KeysBackupState.ReadyToBackUp
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue