mirror of
https://github.com/nextcloud/talk-android
synced 2025-06-20 12:09:45 +01:00
Reformatting
Signed-off-by: Mario Danic <mario@lovelyhq.com>
This commit is contained in:
parent
8441fd2475
commit
fd44934b98
@ -47,102 +47,111 @@ import javax.inject.Inject
|
||||
@AutoInjector(NextcloudTalkApplication::class)
|
||||
open class BaseActivity : AppCompatActivity() {
|
||||
|
||||
@Inject
|
||||
lateinit var eventBus: EventBus
|
||||
@Inject
|
||||
lateinit var eventBus: EventBus
|
||||
|
||||
@Inject
|
||||
lateinit var appPreferences: AppPreferences
|
||||
@Inject
|
||||
lateinit var appPreferences: AppPreferences
|
||||
|
||||
@Inject
|
||||
lateinit var context: Context
|
||||
@Inject
|
||||
lateinit var context: Context
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
NextcloudTalkApplication.sharedApplication!!.componentApplication.inject(this)
|
||||
super.onCreate(savedInstanceState)
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
NextcloudTalkApplication.sharedApplication!!.componentApplication.inject(this)
|
||||
super.onCreate(savedInstanceState)
|
||||
}
|
||||
|
||||
public override fun onResume() {
|
||||
super.onResume()
|
||||
if (appPreferences.isScreenSecured) {
|
||||
window.addFlags(WindowManager.LayoutParams.FLAG_SECURE)
|
||||
} else {
|
||||
window.clearFlags(WindowManager.LayoutParams.FLAG_SECURE)
|
||||
}
|
||||
|
||||
public override fun onResume() {
|
||||
super.onResume()
|
||||
if (appPreferences.isScreenSecured) {
|
||||
window.addFlags(WindowManager.LayoutParams.FLAG_SECURE)
|
||||
} else {
|
||||
window.clearFlags(WindowManager.LayoutParams.FLAG_SECURE)
|
||||
if (appPreferences.isScreenLocked) {
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
|
||||
SecurityUtils.createKey(appPreferences.screenLockTimeout)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun showCertificateDialog(
|
||||
cert: X509Certificate,
|
||||
magicTrustManager: MagicTrustManager,
|
||||
sslErrorHandler: SslErrorHandler?
|
||||
) {
|
||||
val formatter = DateFormat.getDateInstance(DateFormat.LONG)
|
||||
val validFrom = formatter.format(cert.notBefore)
|
||||
val validUntil = formatter.format(cert.notAfter)
|
||||
|
||||
val issuedBy = cert.issuerDN.toString()
|
||||
val issuedFor: String
|
||||
|
||||
try {
|
||||
if (cert.subjectAlternativeNames != null) {
|
||||
val stringBuilder = StringBuilder()
|
||||
for (o in cert.subjectAlternativeNames) {
|
||||
val list = o as List<*>
|
||||
val type = list[0] as Int
|
||||
if (type == 2) {
|
||||
val name = list[1] as String
|
||||
stringBuilder.append("[")
|
||||
.append(type)
|
||||
.append("]")
|
||||
.append(name)
|
||||
.append(" ")
|
||||
}
|
||||
}
|
||||
issuedFor = stringBuilder.toString()
|
||||
} else {
|
||||
issuedFor = cert.subjectDN.name
|
||||
}
|
||||
|
||||
if (appPreferences.isScreenLocked) {
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
|
||||
SecurityUtils.createKey(appPreferences.screenLockTimeout)
|
||||
}
|
||||
}
|
||||
@SuppressLint("StringFormatMatches") val dialogText = String.format(
|
||||
resources
|
||||
.getString(R.string.nc_certificate_dialog_text),
|
||||
issuedBy, issuedFor, validFrom, validUntil
|
||||
)
|
||||
|
||||
LovelyStandardDialog(this)
|
||||
.setTopColorRes(R.color.nc_darkRed)
|
||||
.setNegativeButtonColorRes(R.color.nc_darkRed)
|
||||
.setPositiveButtonColorRes(R.color.colorPrimaryDark)
|
||||
.setIcon(R.drawable.ic_security_white_24dp)
|
||||
.setTitle(R.string.nc_certificate_dialog_title)
|
||||
.setMessage(dialogText)
|
||||
.setPositiveButton(R.string.nc_yes) { v ->
|
||||
magicTrustManager.addCertInTrustStore(cert)
|
||||
sslErrorHandler?.proceed()
|
||||
}
|
||||
.setNegativeButton(R.string.nc_no) { view1 ->
|
||||
sslErrorHandler?.cancel()
|
||||
}
|
||||
.show()
|
||||
|
||||
} catch (e: CertificateParsingException) {
|
||||
Log.d(TAG, "Failed to parse the certificate")
|
||||
}
|
||||
|
||||
fun showCertificateDialog(cert: X509Certificate, magicTrustManager: MagicTrustManager,
|
||||
sslErrorHandler: SslErrorHandler?) {
|
||||
val formatter = DateFormat.getDateInstance(DateFormat.LONG)
|
||||
val validFrom = formatter.format(cert.notBefore)
|
||||
val validUntil = formatter.format(cert.notAfter)
|
||||
}
|
||||
|
||||
val issuedBy = cert.issuerDN.toString()
|
||||
val issuedFor: String
|
||||
@Subscribe(threadMode = ThreadMode.MAIN)
|
||||
fun onMessageEvent(event: CertificateEvent) {
|
||||
showCertificateDialog(event.x509Certificate, event.magicTrustManager, event.sslErrorHandler)
|
||||
}
|
||||
|
||||
try {
|
||||
if (cert.subjectAlternativeNames != null) {
|
||||
val stringBuilder = StringBuilder()
|
||||
for (o in cert.subjectAlternativeNames) {
|
||||
val list = o as List<*>
|
||||
val type = list[0] as Int
|
||||
if (type == 2) {
|
||||
val name = list[1] as String
|
||||
stringBuilder.append("[").append(type).append("]").append(name).append(" ")
|
||||
}
|
||||
}
|
||||
issuedFor = stringBuilder.toString()
|
||||
} else {
|
||||
issuedFor = cert.subjectDN.name
|
||||
}
|
||||
public override fun onStart() {
|
||||
super.onStart()
|
||||
eventBus.register(this)
|
||||
}
|
||||
|
||||
@SuppressLint("StringFormatMatches") val dialogText = String.format(resources
|
||||
.getString(R.string.nc_certificate_dialog_text),
|
||||
issuedBy, issuedFor, validFrom, validUntil)
|
||||
public override fun onStop() {
|
||||
super.onStop()
|
||||
eventBus.unregister(this)
|
||||
}
|
||||
|
||||
LovelyStandardDialog(this)
|
||||
.setTopColorRes(R.color.nc_darkRed)
|
||||
.setNegativeButtonColorRes(R.color.nc_darkRed)
|
||||
.setPositiveButtonColorRes(R.color.colorPrimaryDark)
|
||||
.setIcon(R.drawable.ic_security_white_24dp)
|
||||
.setTitle(R.string.nc_certificate_dialog_title)
|
||||
.setMessage(dialogText)
|
||||
.setPositiveButton(R.string.nc_yes) { v ->
|
||||
magicTrustManager.addCertInTrustStore(cert)
|
||||
sslErrorHandler?.proceed()
|
||||
}
|
||||
.setNegativeButton(R.string.nc_no) { view1 ->
|
||||
sslErrorHandler?.cancel()
|
||||
}
|
||||
.show()
|
||||
|
||||
} catch (e: CertificateParsingException) {
|
||||
Log.d(TAG, "Failed to parse the certificate")
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Subscribe(threadMode = ThreadMode.MAIN)
|
||||
fun onMessageEvent(event: CertificateEvent) {
|
||||
showCertificateDialog(event.x509Certificate, event.magicTrustManager, event.sslErrorHandler)
|
||||
}
|
||||
|
||||
public override fun onStart() {
|
||||
super.onStart()
|
||||
eventBus.register(this)
|
||||
}
|
||||
|
||||
public override fun onStop() {
|
||||
super.onStop()
|
||||
eventBus.unregister(this)
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = "BaseActivity"
|
||||
}
|
||||
companion object {
|
||||
private val TAG = "BaseActivity"
|
||||
}
|
||||
}
|
||||
|
@ -43,54 +43,60 @@ import com.nextcloud.talk.utils.bundle.BundleKeys
|
||||
@AutoInjector(NextcloudTalkApplication::class)
|
||||
class MagicCallActivity : BaseActivity() {
|
||||
|
||||
@BindView(R.id.controller_container)
|
||||
lateinit var container: ViewGroup
|
||||
@BindView(R.id.controller_container)
|
||||
lateinit var container: ViewGroup
|
||||
|
||||
private var router: Router? = null
|
||||
private var router: Router? = null
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
NextcloudTalkApplication.sharedApplication!!.componentApplication.inject(this)
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
NextcloudTalkApplication.sharedApplication!!.componentApplication.inject(this)
|
||||
|
||||
requestWindowFeature(Window.FEATURE_NO_TITLE)
|
||||
window.addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN or
|
||||
WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON or
|
||||
WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD or WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED or
|
||||
WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON)
|
||||
window.decorView.systemUiVisibility = systemUiVisibility
|
||||
requestWindowFeature(Window.FEATURE_NO_TITLE)
|
||||
window.addFlags(
|
||||
WindowManager.LayoutParams.FLAG_FULLSCREEN or
|
||||
WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON or
|
||||
WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD or WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED or
|
||||
WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON
|
||||
)
|
||||
window.decorView.systemUiVisibility = systemUiVisibility
|
||||
|
||||
setContentView(R.layout.activity_magic_call)
|
||||
setContentView(R.layout.activity_magic_call)
|
||||
|
||||
ButterKnife.bind(this)
|
||||
router = Conductor.attachRouter(this, container, savedInstanceState)
|
||||
router!!.setPopsLastView(false)
|
||||
ButterKnife.bind(this)
|
||||
router = Conductor.attachRouter(this, container, savedInstanceState)
|
||||
router!!.setPopsLastView(false)
|
||||
|
||||
if (!router!!.hasRootController()) {
|
||||
if (intent.getBooleanExtra(BundleKeys.KEY_FROM_NOTIFICATION_START_CALL, false)) {
|
||||
router!!.setRoot(RouterTransaction.with(CallNotificationController(intent.extras))
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler()))
|
||||
} else {
|
||||
router!!.setRoot(RouterTransaction.with(CallController(intent.extras))
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler()))
|
||||
}
|
||||
}
|
||||
if (!router!!.hasRootController()) {
|
||||
if (intent.getBooleanExtra(BundleKeys.KEY_FROM_NOTIFICATION_START_CALL, false)) {
|
||||
router!!.setRoot(
|
||||
RouterTransaction.with(CallNotificationController(intent.extras))
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler())
|
||||
)
|
||||
} else {
|
||||
router!!.setRoot(
|
||||
RouterTransaction.with(CallController(intent.extras))
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler())
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun onConfigurationChanged(newConfig: Configuration) {
|
||||
super.onConfigurationChanged(newConfig)
|
||||
eventBus.post(ConfigurationChangeEvent())
|
||||
}
|
||||
override fun onConfigurationChanged(newConfig: Configuration) {
|
||||
super.onConfigurationChanged(newConfig)
|
||||
eventBus.post(ConfigurationChangeEvent())
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = "MagicCallActivity"
|
||||
companion object {
|
||||
private val TAG = "MagicCallActivity"
|
||||
|
||||
private val systemUiVisibility: Int
|
||||
get() {
|
||||
var flags = View.SYSTEM_UI_FLAG_HIDE_NAVIGATION or View.SYSTEM_UI_FLAG_FULLSCREEN
|
||||
flags = flags or View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY
|
||||
return flags
|
||||
}
|
||||
}
|
||||
private val systemUiVisibility: Int
|
||||
get() {
|
||||
var flags = View.SYSTEM_UI_FLAG_HIDE_NAVIGATION or View.SYSTEM_UI_FLAG_FULLSCREEN
|
||||
flags = flags or View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY
|
||||
return flags
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -39,7 +39,6 @@ import com.google.android.material.appbar.MaterialToolbar
|
||||
import com.nextcloud.talk.R
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication
|
||||
import com.nextcloud.talk.controllers.CallNotificationController
|
||||
import com.nextcloud.talk.controllers.ConversationsListController
|
||||
import com.nextcloud.talk.controllers.LockedController
|
||||
import com.nextcloud.talk.controllers.ServerSelectionController
|
||||
import com.nextcloud.talk.controllers.base.providers.ActionBarProvider
|
||||
@ -56,117 +55,129 @@ import javax.inject.Inject
|
||||
@AutoInjector(NextcloudTalkApplication::class)
|
||||
class MainActivity : BaseActivity(), ActionBarProvider {
|
||||
|
||||
@BindView(R.id.toolbar)
|
||||
lateinit var toolbar: MaterialToolbar
|
||||
@BindView(R.id.controller_container)
|
||||
lateinit var container: ViewGroup
|
||||
@BindView(R.id.toolbar)
|
||||
lateinit var toolbar: MaterialToolbar
|
||||
@BindView(R.id.controller_container)
|
||||
lateinit var container: ViewGroup
|
||||
|
||||
@Inject
|
||||
lateinit var userUtils: UserUtils
|
||||
@Inject
|
||||
lateinit var dataStore: ReactiveEntityStore<Persistable>
|
||||
@Inject
|
||||
lateinit var sqlCipherDatabaseSource: SqlCipherDatabaseSource
|
||||
@Inject
|
||||
lateinit var userUtils: UserUtils
|
||||
@Inject
|
||||
lateinit var dataStore: ReactiveEntityStore<Persistable>
|
||||
@Inject
|
||||
lateinit var sqlCipherDatabaseSource: SqlCipherDatabaseSource
|
||||
|
||||
private var router: Router? = null
|
||||
private var router: Router? = null
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
|
||||
setContentView(R.layout.activity_main)
|
||||
setContentView(R.layout.activity_main)
|
||||
|
||||
NextcloudTalkApplication.sharedApplication!!.componentApplication.inject(this)
|
||||
ButterKnife.bind(this)
|
||||
NextcloudTalkApplication.sharedApplication!!.componentApplication.inject(this)
|
||||
ButterKnife.bind(this)
|
||||
|
||||
setSupportActionBar(toolbar)
|
||||
setSupportActionBar(toolbar)
|
||||
|
||||
router = Conductor.attachRouter(this, container, savedInstanceState)
|
||||
router = Conductor.attachRouter(this, container, savedInstanceState)
|
||||
|
||||
var hasDb = true
|
||||
var hasDb = true
|
||||
|
||||
try {
|
||||
sqlCipherDatabaseSource.writableDatabase
|
||||
} catch (exception: Exception) {
|
||||
hasDb = false
|
||||
}
|
||||
|
||||
if (intent.hasExtra(BundleKeys.KEY_FROM_NOTIFICATION_START_CALL)) {
|
||||
if (!router!!.hasRootController()) {
|
||||
router!!.setRoot(RouterTransaction.with(ConversationsListView())
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler()))
|
||||
}
|
||||
onNewIntent(intent)
|
||||
} else if (!router!!.hasRootController()) {
|
||||
if (hasDb) {
|
||||
if (userUtils.anyUserExists()) {
|
||||
router!!.setRoot(RouterTransaction.with(ConversationsListView())
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler()))
|
||||
} else {
|
||||
router!!.setRoot(RouterTransaction.with(ServerSelectionController())
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler()))
|
||||
}
|
||||
} else {
|
||||
router!!.setRoot(RouterTransaction.with(ServerSelectionController())
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler()))
|
||||
|
||||
}
|
||||
}
|
||||
try {
|
||||
sqlCipherDatabaseSource.writableDatabase
|
||||
} catch (exception: Exception) {
|
||||
hasDb = false
|
||||
}
|
||||
|
||||
override fun onStart() {
|
||||
super.onStart()
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
|
||||
checkIfWeAreSecure()
|
||||
if (intent.hasExtra(BundleKeys.KEY_FROM_NOTIFICATION_START_CALL)) {
|
||||
if (!router!!.hasRootController()) {
|
||||
router!!.setRoot(
|
||||
RouterTransaction.with(ConversationsListView())
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler())
|
||||
)
|
||||
}
|
||||
onNewIntent(intent)
|
||||
} else if (!router!!.hasRootController()) {
|
||||
if (hasDb) {
|
||||
if (userUtils.anyUserExists()) {
|
||||
router!!.setRoot(
|
||||
RouterTransaction.with(ConversationsListView())
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler())
|
||||
)
|
||||
} else {
|
||||
router!!.setRoot(
|
||||
RouterTransaction.with(ServerSelectionController())
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler())
|
||||
)
|
||||
}
|
||||
} else {
|
||||
router!!.setRoot(
|
||||
RouterTransaction.with(ServerSelectionController())
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler())
|
||||
)
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun onStart() {
|
||||
super.onStart()
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
|
||||
checkIfWeAreSecure()
|
||||
}
|
||||
}
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.M)
|
||||
fun checkIfWeAreSecure() {
|
||||
val keyguardManager = getSystemService(Context.KEYGUARD_SERVICE) as KeyguardManager
|
||||
if (keyguardManager.isKeyguardSecure && appPreferences.isScreenLocked) {
|
||||
if (!SecurityUtils.checkIfWeAreAuthenticated(appPreferences.screenLockTimeout)) {
|
||||
if (router != null && router!!.getControllerWithTag(LockedController.TAG) == null) {
|
||||
router!!.pushController(
|
||||
RouterTransaction.with(LockedController())
|
||||
.pushChangeHandler(VerticalChangeHandler())
|
||||
.popChangeHandler(VerticalChangeHandler())
|
||||
.tag(LockedController.TAG)
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun onNewIntent(intent: Intent) {
|
||||
super.onNewIntent(intent)
|
||||
|
||||
if (intent.hasExtra(BundleKeys.KEY_FROM_NOTIFICATION_START_CALL)) {
|
||||
if (intent.getBooleanExtra(BundleKeys.KEY_FROM_NOTIFICATION_START_CALL, false)) {
|
||||
router!!.pushController(
|
||||
RouterTransaction.with(CallNotificationController(intent.extras))
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler())
|
||||
)
|
||||
} else {
|
||||
ConductorRemapping.remapChatController(
|
||||
router!!, intent.getLongExtra(BundleKeys.KEY_INTERNAL_USER_ID, -1),
|
||||
intent.getStringExtra(BundleKeys.KEY_ROOM_TOKEN), intent.extras!!, false
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun onBackPressed() {
|
||||
if (router!!.getControllerWithTag(LockedController.TAG) != null) {
|
||||
return
|
||||
}
|
||||
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.M)
|
||||
fun checkIfWeAreSecure() {
|
||||
val keyguardManager = getSystemService(Context.KEYGUARD_SERVICE) as KeyguardManager
|
||||
if (keyguardManager.isKeyguardSecure && appPreferences.isScreenLocked) {
|
||||
if (!SecurityUtils.checkIfWeAreAuthenticated(appPreferences.screenLockTimeout)) {
|
||||
if (router != null && router!!.getControllerWithTag(LockedController.TAG) == null) {
|
||||
router!!.pushController(RouterTransaction.with(LockedController())
|
||||
.pushChangeHandler(VerticalChangeHandler())
|
||||
.popChangeHandler(VerticalChangeHandler())
|
||||
.tag(LockedController.TAG))
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!router!!.handleBack()) {
|
||||
super.onBackPressed()
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
override fun onNewIntent(intent: Intent) {
|
||||
super.onNewIntent(intent)
|
||||
|
||||
if (intent.hasExtra(BundleKeys.KEY_FROM_NOTIFICATION_START_CALL)) {
|
||||
if (intent.getBooleanExtra(BundleKeys.KEY_FROM_NOTIFICATION_START_CALL, false)) {
|
||||
router!!.pushController(RouterTransaction.with(CallNotificationController(intent.extras))
|
||||
.pushChangeHandler(HorizontalChangeHandler())
|
||||
.popChangeHandler(HorizontalChangeHandler()))
|
||||
} else {
|
||||
ConductorRemapping.remapChatController(router!!, intent.getLongExtra(BundleKeys.KEY_INTERNAL_USER_ID, -1),
|
||||
intent.getStringExtra(BundleKeys.KEY_ROOM_TOKEN), intent.extras!!, false)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun onBackPressed() {
|
||||
if (router!!.getControllerWithTag(LockedController.TAG) != null) {
|
||||
return
|
||||
}
|
||||
|
||||
if (!router!!.handleBack()) {
|
||||
super.onBackPressed()
|
||||
}
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = "MainActivity"
|
||||
}
|
||||
companion object {
|
||||
private val TAG = "MainActivity"
|
||||
}
|
||||
}
|
||||
|
@ -48,126 +48,134 @@ import eu.davidea.viewholders.FlexibleViewHolder;
|
||||
import java.util.List;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
public class AdvancedUserItem extends AbstractFlexibleItem<AdvancedUserItem.UserItemViewHolder> implements
|
||||
IFilterable<String> {
|
||||
public class AdvancedUserItem extends AbstractFlexibleItem<AdvancedUserItem.UserItemViewHolder>
|
||||
implements
|
||||
IFilterable<String> {
|
||||
|
||||
private Participant participant;
|
||||
private UserEntity userEntity;
|
||||
@Nullable
|
||||
private Account account;
|
||||
private Participant participant;
|
||||
private UserEntity userEntity;
|
||||
@Nullable
|
||||
private Account account;
|
||||
|
||||
public AdvancedUserItem(Participant participant, UserEntity userEntity, @Nullable Account account) {
|
||||
this.participant = participant;
|
||||
this.userEntity = userEntity;
|
||||
this.account = account;
|
||||
public AdvancedUserItem(Participant participant, UserEntity userEntity,
|
||||
@Nullable Account account) {
|
||||
this.participant = participant;
|
||||
this.userEntity = userEntity;
|
||||
this.account = account;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof AdvancedUserItem) {
|
||||
AdvancedUserItem inItem = (AdvancedUserItem) o;
|
||||
return participant.equals(inItem.getModel());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return participant.hashCode();
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the model object
|
||||
*/
|
||||
|
||||
public Participant getModel() {
|
||||
return participant;
|
||||
}
|
||||
|
||||
public UserEntity getEntity() {
|
||||
return userEntity;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public Account getAccount() {
|
||||
return account;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_conversation;
|
||||
}
|
||||
|
||||
@Override
|
||||
public UserItemViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new UserItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter adapter, UserItemViewHolder holder, int position,
|
||||
List payloads) {
|
||||
holder.avatarImageView.setController(null);
|
||||
|
||||
if (adapter.hasFilter()) {
|
||||
FlexibleUtils.highlightText(holder.contactDisplayName, participant.getName(),
|
||||
String.valueOf(adapter.getFilter(String.class)),
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.colorPrimary));
|
||||
} else {
|
||||
holder.contactDisplayName.setText(participant.getName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof AdvancedUserItem) {
|
||||
AdvancedUserItem inItem = (AdvancedUserItem) o;
|
||||
return participant.equals(inItem.getModel());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
holder.serverUrl.setText(userEntity.getBaseUrl());
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return participant.hashCode();
|
||||
if (userEntity != null && userEntity.getBaseUrl() != null && userEntity.getBaseUrl()
|
||||
.startsWith("http://") || userEntity.getBaseUrl().startsWith("https://")) {
|
||||
holder.avatarImageView.setVisibility(View.VISIBLE);
|
||||
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.avatarImageView.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(
|
||||
ApiUtils.getUrlForAvatarWithName(userEntity.getBaseUrl(),
|
||||
participant.getUserId(), R.dimen.avatar_size), null))
|
||||
.build();
|
||||
holder.avatarImageView.setController(draweeController);
|
||||
} else {
|
||||
holder.avatarImageView.setVisibility(View.GONE);
|
||||
RelativeLayout.LayoutParams layoutParams =
|
||||
(RelativeLayout.LayoutParams) holder.linearLayout.getLayoutParams();
|
||||
layoutParams.setMarginStart(
|
||||
(int) NextcloudTalkApplication.Companion.getSharedApplication().getApplicationContext()
|
||||
.getResources().getDimension(R.dimen.activity_horizontal_margin));
|
||||
layoutParams.addRule(RelativeLayout.ALIGN_PARENT_START);
|
||||
holder.linearLayout.setLayoutParams(layoutParams);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return participant.getName() != null &&
|
||||
Pattern.compile(constraint, Pattern.CASE_INSENSITIVE | Pattern.LITERAL)
|
||||
.matcher(participant.getName().trim())
|
||||
.find();
|
||||
}
|
||||
|
||||
static class UserItemViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.name_text)
|
||||
public EmojiTextView contactDisplayName;
|
||||
@BindView(R.id.secondary_text)
|
||||
public TextView serverUrl;
|
||||
@BindView(R.id.avatar_image)
|
||||
public SimpleDraweeView avatarImageView;
|
||||
@BindView(R.id.linear_layout)
|
||||
LinearLayout linearLayout;
|
||||
@BindView(R.id.more_menu)
|
||||
ImageButton moreMenuButton;
|
||||
@BindView(R.id.password_protected_image_view)
|
||||
ImageView passwordProtectedImageView;
|
||||
|
||||
/**
|
||||
* @return the model object
|
||||
* Default constructor.
|
||||
*/
|
||||
|
||||
public Participant getModel() {
|
||||
return participant;
|
||||
}
|
||||
|
||||
public UserEntity getEntity() {
|
||||
return userEntity;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public Account getAccount() {
|
||||
return account;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_conversation;
|
||||
}
|
||||
|
||||
@Override
|
||||
public UserItemViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new UserItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter adapter, UserItemViewHolder holder, int position, List payloads) {
|
||||
holder.avatarImageView.setController(null);
|
||||
|
||||
if (adapter.hasFilter()) {
|
||||
FlexibleUtils.highlightText(holder.contactDisplayName, participant.getName(),
|
||||
String.valueOf(adapter.getFilter(String.class)), NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.colorPrimary));
|
||||
} else {
|
||||
holder.contactDisplayName.setText(participant.getName());
|
||||
}
|
||||
|
||||
holder.serverUrl.setText(userEntity.getBaseUrl());
|
||||
|
||||
if (userEntity != null && userEntity.getBaseUrl() != null && userEntity.getBaseUrl().startsWith("http://") || userEntity.getBaseUrl().startsWith("https://")) {
|
||||
holder.avatarImageView.setVisibility(View.VISIBLE);
|
||||
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.avatarImageView.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(ApiUtils.getUrlForAvatarWithName(userEntity.getBaseUrl(),
|
||||
participant.getUserId(), R.dimen.avatar_size), null))
|
||||
.build();
|
||||
holder.avatarImageView.setController(draweeController);
|
||||
|
||||
} else {
|
||||
holder.avatarImageView.setVisibility(View.GONE);
|
||||
RelativeLayout.LayoutParams layoutParams = (RelativeLayout.LayoutParams) holder.linearLayout.getLayoutParams();
|
||||
layoutParams.setMarginStart((int) NextcloudTalkApplication.Companion.getSharedApplication().getApplicationContext()
|
||||
.getResources().getDimension(R.dimen.activity_horizontal_margin));
|
||||
layoutParams.addRule(RelativeLayout.ALIGN_PARENT_START);
|
||||
holder.linearLayout.setLayoutParams(layoutParams);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return participant.getName() != null &&
|
||||
Pattern.compile(constraint, Pattern.CASE_INSENSITIVE | Pattern.LITERAL).matcher(participant.getName().trim()).find();
|
||||
}
|
||||
|
||||
|
||||
static class UserItemViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.name_text)
|
||||
public EmojiTextView contactDisplayName;
|
||||
@BindView(R.id.secondary_text)
|
||||
public TextView serverUrl;
|
||||
@BindView(R.id.avatar_image)
|
||||
public SimpleDraweeView avatarImageView;
|
||||
@BindView(R.id.linear_layout)
|
||||
LinearLayout linearLayout;
|
||||
@BindView(R.id.more_menu)
|
||||
ImageButton moreMenuButton;
|
||||
@BindView(R.id.password_protected_image_view)
|
||||
ImageView passwordProtectedImageView;
|
||||
|
||||
/**
|
||||
* Default constructor.
|
||||
*/
|
||||
UserItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
moreMenuButton.setVisibility(View.GONE);
|
||||
passwordProtectedImageView.setVisibility(View.GONE);
|
||||
}
|
||||
UserItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
moreMenuButton.setVisibility(View.GONE);
|
||||
passwordProtectedImageView.setVisibility(View.GONE);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -39,86 +39,89 @@ import eu.davidea.viewholders.FlexibleViewHolder;
|
||||
import java.util.List;
|
||||
|
||||
public class AppItem extends AbstractFlexibleItem<AppItem.AppItemViewHolder> {
|
||||
private String title;
|
||||
private String packageName;
|
||||
private String name;
|
||||
@Nullable
|
||||
private Drawable drawable;
|
||||
private String title;
|
||||
private String packageName;
|
||||
private String name;
|
||||
@Nullable
|
||||
private Drawable drawable;
|
||||
|
||||
public AppItem(String title, String packageName, String name, @Nullable Drawable drawable) {
|
||||
this.title = title;
|
||||
this.packageName = packageName;
|
||||
this.name = name;
|
||||
this.drawable = drawable;
|
||||
public AppItem(String title, String packageName, String name, @Nullable Drawable drawable) {
|
||||
this.title = title;
|
||||
this.packageName = packageName;
|
||||
this.name = name;
|
||||
this.drawable = drawable;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof AppItem) {
|
||||
AppItem inItem = (AppItem) o;
|
||||
return title.equals(inItem.getTitle())
|
||||
&& packageName.equals(inItem.getPackageName())
|
||||
&& name.equals(inItem
|
||||
.getName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof AppItem) {
|
||||
AppItem inItem = (AppItem) o;
|
||||
return title.equals(inItem.getTitle()) && packageName.equals(inItem.getPackageName()) && name.equals(inItem
|
||||
.getName());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
return false;
|
||||
public String getTitle() {
|
||||
return title;
|
||||
}
|
||||
|
||||
public String getPackageName() {
|
||||
return packageName;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_app;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, AppItemViewHolder holder,
|
||||
int position, List<Object> payloads) {
|
||||
if (drawable != null) {
|
||||
holder.iconImageView.setVisibility(View.VISIBLE);
|
||||
holder.iconImageView.setImageDrawable(drawable);
|
||||
} else {
|
||||
holder.iconImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
public String getTitle() {
|
||||
return title;
|
||||
if (position == 0) {
|
||||
Spannable spannableString = new SpannableString(title);
|
||||
spannableString.setSpan(
|
||||
new ForegroundColorSpan(NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.grey_600)), 0,
|
||||
spannableString.length(),
|
||||
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
|
||||
holder.appTitleTextView.setText(spannableString);
|
||||
} else {
|
||||
holder.appTitleTextView.setText(title);
|
||||
}
|
||||
}
|
||||
|
||||
public String getPackageName() {
|
||||
return packageName;
|
||||
@Override
|
||||
public AppItem.AppItemViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new AppItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
static class AppItemViewHolder extends FlexibleViewHolder {
|
||||
@BindView(R.id.icon_image_view)
|
||||
public ImageView iconImageView;
|
||||
@BindView(R.id.app_title_text_view)
|
||||
public TextView appTitleTextView;
|
||||
|
||||
/**
|
||||
* Default constructor.
|
||||
*/
|
||||
AppItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_app;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, AppItemViewHolder holder, int position, List<Object> payloads) {
|
||||
if (drawable != null) {
|
||||
holder.iconImageView.setVisibility(View.VISIBLE);
|
||||
holder.iconImageView.setImageDrawable(drawable);
|
||||
} else {
|
||||
holder.iconImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
if (position == 0) {
|
||||
Spannable spannableString = new SpannableString(title);
|
||||
spannableString.setSpan(new ForegroundColorSpan(NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.grey_600)), 0,
|
||||
spannableString.length(),
|
||||
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
|
||||
holder.appTitleTextView.setText(spannableString);
|
||||
} else {
|
||||
holder.appTitleTextView.setText(title);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public AppItem.AppItemViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new AppItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
static class AppItemViewHolder extends FlexibleViewHolder {
|
||||
@BindView(R.id.icon_image_view)
|
||||
public ImageView iconImageView;
|
||||
@BindView(R.id.app_title_text_view)
|
||||
public TextView appTitleTextView;
|
||||
|
||||
/**
|
||||
* Default constructor.
|
||||
*/
|
||||
AppItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -48,138 +48,145 @@ import java.util.List;
|
||||
import java.util.regex.Pattern;
|
||||
import org.greenrobot.eventbus.EventBus;
|
||||
|
||||
public class CallItem extends AbstractFlexibleItem<CallItem.RoomItemViewHolder> implements IFilterable<String> {
|
||||
public class CallItem extends AbstractFlexibleItem<CallItem.RoomItemViewHolder>
|
||||
implements IFilterable<String> {
|
||||
|
||||
private Conversation conversation;
|
||||
private UserEntity userEntity;
|
||||
private Conversation conversation;
|
||||
private UserEntity userEntity;
|
||||
|
||||
public CallItem(Conversation conversation, UserEntity userEntity) {
|
||||
this.conversation = conversation;
|
||||
this.userEntity = userEntity;
|
||||
public CallItem(Conversation conversation, UserEntity userEntity) {
|
||||
this.conversation = conversation;
|
||||
this.userEntity = userEntity;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof CallItem) {
|
||||
CallItem inItem = (CallItem) o;
|
||||
return conversation.equals(inItem.getModel());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return conversation.hashCode();
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the model object
|
||||
*/
|
||||
|
||||
public Conversation getModel() {
|
||||
return conversation;
|
||||
}
|
||||
|
||||
/**
|
||||
* Filter is applied to the model fields.
|
||||
*/
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_conversation;
|
||||
}
|
||||
|
||||
@Override
|
||||
public RoomItemViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new RoomItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(final FlexibleAdapter adapter, RoomItemViewHolder holder, int position,
|
||||
List payloads) {
|
||||
if (adapter.hasFilter()) {
|
||||
FlexibleUtils.highlightText(holder.roomDisplayName, conversation.getDisplayName(),
|
||||
String.valueOf(adapter.getFilter(String.class)),
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.colorPrimary));
|
||||
} else {
|
||||
holder.roomDisplayName.setText(conversation.getDisplayName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof CallItem) {
|
||||
CallItem inItem = (CallItem) o;
|
||||
return conversation.equals(inItem.getModel());
|
||||
}
|
||||
return false;
|
||||
if (conversation.getLastPing() == 0) {
|
||||
holder.roomLastPing.setText(R.string.nc_never);
|
||||
} else {
|
||||
holder.roomLastPing.setText(
|
||||
DateUtils.getRelativeTimeSpanString(conversation.getLastPing() * 1000L,
|
||||
System.currentTimeMillis(), 0, DateUtils.FORMAT_ABBREV_RELATIVE));
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return conversation.hashCode();
|
||||
if (conversation.hasPassword) {
|
||||
holder.passwordProtectedImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.passwordProtectedImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the model object
|
||||
*/
|
||||
Resources resources = NextcloudTalkApplication.Companion.getSharedApplication().getResources();
|
||||
switch (conversation.getType()) {
|
||||
case ROOM_TYPE_ONE_TO_ONE_CALL:
|
||||
holder.avatarImageView.setVisibility(View.VISIBLE);
|
||||
|
||||
public Conversation getModel() {
|
||||
return conversation;
|
||||
}
|
||||
holder.moreMenuButton.setContentDescription(String.format(resources.getString(R.string
|
||||
.nc_description_more_menu_one_to_one), conversation.getDisplayName()));
|
||||
|
||||
/**
|
||||
* Filter is applied to the model fields.
|
||||
*/
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_conversation;
|
||||
}
|
||||
|
||||
@Override
|
||||
public RoomItemViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new RoomItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(final FlexibleAdapter adapter, RoomItemViewHolder holder, int position, List payloads) {
|
||||
if (adapter.hasFilter()) {
|
||||
FlexibleUtils.highlightText(holder.roomDisplayName, conversation.getDisplayName(),
|
||||
String.valueOf(adapter.getFilter(String.class)), NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.colorPrimary));
|
||||
if (!TextUtils.isEmpty(conversation.getName())) {
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.avatarImageView.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(
|
||||
ApiUtils.getUrlForAvatarWithName(userEntity.getBaseUrl(),
|
||||
conversation.getName(),
|
||||
R.dimen.avatar_size), null))
|
||||
.build();
|
||||
holder.avatarImageView.setController(draweeController);
|
||||
} else {
|
||||
holder.roomDisplayName.setText(conversation.getDisplayName());
|
||||
holder.avatarImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
if (conversation.getLastPing() == 0) {
|
||||
holder.roomLastPing.setText(R.string.nc_never);
|
||||
} else {
|
||||
holder.roomLastPing.setText(DateUtils.getRelativeTimeSpanString(conversation.getLastPing() * 1000L,
|
||||
System.currentTimeMillis(), 0, DateUtils.FORMAT_ABBREV_RELATIVE));
|
||||
}
|
||||
|
||||
if (conversation.hasPassword) {
|
||||
holder.passwordProtectedImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.passwordProtectedImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
Resources resources = NextcloudTalkApplication.Companion.getSharedApplication().getResources();
|
||||
switch (conversation.getType()) {
|
||||
case ROOM_TYPE_ONE_TO_ONE_CALL:
|
||||
holder.avatarImageView.setVisibility(View.VISIBLE);
|
||||
|
||||
holder.moreMenuButton.setContentDescription(String.format(resources.getString(R.string
|
||||
.nc_description_more_menu_one_to_one), conversation.getDisplayName()));
|
||||
|
||||
if (!TextUtils.isEmpty(conversation.getName())) {
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.avatarImageView.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(ApiUtils.getUrlForAvatarWithName(userEntity.getBaseUrl(),
|
||||
conversation.getName(),
|
||||
R.dimen.avatar_size), null))
|
||||
.build();
|
||||
holder.avatarImageView.setController(draweeController);
|
||||
} else {
|
||||
holder.avatarImageView.setVisibility(View.GONE);
|
||||
}
|
||||
break;
|
||||
case ROOM_GROUP_CALL:
|
||||
holder.moreMenuButton.setContentDescription(String.format(resources.getString(R.string
|
||||
.nc_description_more_menu_group), conversation.getDisplayName()));
|
||||
holder.avatarImageView.setActualImageResource(R.drawable.ic_people_group_white_24px);
|
||||
holder.avatarImageView.setVisibility(View.VISIBLE);
|
||||
break;
|
||||
case ROOM_PUBLIC_CALL:
|
||||
holder.moreMenuButton.setContentDescription(String.format(resources.getString(R.string
|
||||
.nc_description_more_menu_public), conversation.getDisplayName()));
|
||||
holder.avatarImageView.setActualImageResource(R.drawable.ic_link_white_24px);
|
||||
holder.avatarImageView.setVisibility(View.VISIBLE);
|
||||
break;
|
||||
default:
|
||||
holder.avatarImageView.setVisibility(View.GONE);
|
||||
|
||||
}
|
||||
|
||||
holder.moreMenuButton.setOnClickListener(view -> EventBus.getDefault().post(new MoreMenuClickEvent(conversation)));
|
||||
break;
|
||||
case ROOM_GROUP_CALL:
|
||||
holder.moreMenuButton.setContentDescription(String.format(resources.getString(R.string
|
||||
.nc_description_more_menu_group), conversation.getDisplayName()));
|
||||
holder.avatarImageView.setActualImageResource(R.drawable.ic_people_group_white_24px);
|
||||
holder.avatarImageView.setVisibility(View.VISIBLE);
|
||||
break;
|
||||
case ROOM_PUBLIC_CALL:
|
||||
holder.moreMenuButton.setContentDescription(String.format(resources.getString(R.string
|
||||
.nc_description_more_menu_public), conversation.getDisplayName()));
|
||||
holder.avatarImageView.setActualImageResource(R.drawable.ic_link_white_24px);
|
||||
holder.avatarImageView.setVisibility(View.VISIBLE);
|
||||
break;
|
||||
default:
|
||||
holder.avatarImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return conversation.getDisplayName() != null &&
|
||||
Pattern.compile(constraint, Pattern.CASE_INSENSITIVE | Pattern.LITERAL).matcher(conversation.getDisplayName().trim()).find();
|
||||
}
|
||||
|
||||
static class RoomItemViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.name_text)
|
||||
public EmojiTextView roomDisplayName;
|
||||
@BindView(R.id.secondary_text)
|
||||
public EmojiTextView roomLastPing;
|
||||
@BindView(R.id.avatar_image)
|
||||
public SimpleDraweeView avatarImageView;
|
||||
@BindView(R.id.more_menu)
|
||||
public ImageButton moreMenuButton;
|
||||
@BindView(R.id.password_protected_image_view)
|
||||
ImageView passwordProtectedImageView;
|
||||
|
||||
RoomItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
holder.moreMenuButton.setOnClickListener(
|
||||
view -> EventBus.getDefault().post(new MoreMenuClickEvent(conversation)));
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return conversation.getDisplayName() != null &&
|
||||
Pattern.compile(constraint, Pattern.CASE_INSENSITIVE | Pattern.LITERAL)
|
||||
.matcher(conversation.getDisplayName().trim())
|
||||
.find();
|
||||
}
|
||||
|
||||
static class RoomItemViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.name_text)
|
||||
public EmojiTextView roomDisplayName;
|
||||
@BindView(R.id.secondary_text)
|
||||
public EmojiTextView roomLastPing;
|
||||
@BindView(R.id.avatar_image)
|
||||
public SimpleDraweeView avatarImageView;
|
||||
@BindView(R.id.more_menu)
|
||||
public ImageButton moreMenuButton;
|
||||
@BindView(R.id.password_protected_image_view)
|
||||
ImageView passwordProtectedImageView;
|
||||
|
||||
RoomItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -35,11 +35,11 @@ import butterknife.ButterKnife;
|
||||
import com.facebook.drawee.backends.pipeline.Fresco;
|
||||
import com.facebook.drawee.interfaces.DraweeController;
|
||||
import com.facebook.drawee.view.SimpleDraweeView;
|
||||
import com.nextcloud.talk.models.json.conversations.Conversation;
|
||||
import com.nextcloud.talk.R;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.models.json.chat.ChatMessage;
|
||||
import com.nextcloud.talk.models.json.conversations.Conversation;
|
||||
import com.nextcloud.talk.utils.ApiUtils;
|
||||
import com.nextcloud.talk.utils.DisplayUtils;
|
||||
import eu.davidea.flexibleadapter.FlexibleAdapter;
|
||||
@ -51,215 +51,233 @@ import eu.davidea.viewholders.FlexibleViewHolder;
|
||||
import java.util.List;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
public class ConversationItem extends AbstractFlexibleItem<ConversationItem.ConversationItemViewHolder> implements
|
||||
IFilterable<String> {
|
||||
public class ConversationItem
|
||||
extends AbstractFlexibleItem<ConversationItem.ConversationItemViewHolder> implements
|
||||
IFilterable<String> {
|
||||
|
||||
private Conversation conversation;
|
||||
private UserEntity userEntity;
|
||||
private Context context;
|
||||
|
||||
private Conversation conversation;
|
||||
private UserEntity userEntity;
|
||||
private Context context;
|
||||
public ConversationItem(Conversation conversation, UserEntity userEntity,
|
||||
Context activityContext) {
|
||||
this.conversation = conversation;
|
||||
this.userEntity = userEntity;
|
||||
this.context = activityContext;
|
||||
}
|
||||
|
||||
public ConversationItem(Conversation conversation, UserEntity userEntity,
|
||||
Context activityContext) {
|
||||
this.conversation = conversation;
|
||||
this.userEntity = userEntity;
|
||||
this.context = activityContext;
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof ConversationItem) {
|
||||
ConversationItem inItem = (ConversationItem) o;
|
||||
return conversation.equals(inItem.getModel());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public Conversation getModel() {
|
||||
return conversation;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return conversation.hashCode();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_conversation_with_last_message;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ConversationItemViewHolder createViewHolder(View view,
|
||||
FlexibleAdapter<IFlexible> adapter) {
|
||||
return new ConversationItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, ConversationItemViewHolder holder,
|
||||
int position, List<Object> payloads) {
|
||||
Context appContext =
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getApplicationContext();
|
||||
|
||||
holder.dialogAvatar.setController(null);
|
||||
|
||||
if (adapter.hasFilter()) {
|
||||
FlexibleUtils.highlightText(holder.dialogName, conversation.getDisplayName(),
|
||||
String.valueOf(adapter.getFilter(String.class)),
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.colorPrimary));
|
||||
} else {
|
||||
holder.dialogName.setText(conversation.getDisplayName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof ConversationItem) {
|
||||
ConversationItem inItem = (ConversationItem) o;
|
||||
return conversation.equals(inItem.getModel());
|
||||
}
|
||||
return false;
|
||||
if (conversation.getUnreadMessages() > 0) {
|
||||
holder.dialogUnreadBubble.setVisibility(View.VISIBLE);
|
||||
if (conversation.getUnreadMessages() < 100) {
|
||||
holder.dialogUnreadBubble.setText(Long.toString(conversation.getUnreadMessages()));
|
||||
} else {
|
||||
holder.dialogUnreadBubble.setText("99+");
|
||||
}
|
||||
|
||||
if (conversation.isUnreadMention()) {
|
||||
holder.dialogUnreadBubble.setBackground(
|
||||
context.getDrawable(R.drawable.bubble_circle_unread_mention));
|
||||
} else {
|
||||
holder.dialogUnreadBubble.setBackground(
|
||||
context.getDrawable(R.drawable.bubble_circle_unread));
|
||||
}
|
||||
} else {
|
||||
holder.dialogUnreadBubble.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
public Conversation getModel() {
|
||||
return conversation;
|
||||
if (conversation.isHasPassword()) {
|
||||
holder.passwordProtectedRoomImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.passwordProtectedRoomImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return conversation.hashCode();
|
||||
if (conversation.isFavorite()) {
|
||||
holder.pinnedConversationImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.pinnedConversationImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_conversation_with_last_message;
|
||||
}
|
||||
if (conversation.getLastMessage() != null) {
|
||||
holder.dialogDate.setVisibility(View.VISIBLE);
|
||||
holder.dialogDate.setText(
|
||||
DateUtils.getRelativeTimeSpanString(conversation.getLastActivity() * 1000L,
|
||||
System.currentTimeMillis(), 0, DateUtils.FORMAT_ABBREV_RELATIVE));
|
||||
|
||||
@Override
|
||||
public ConversationItemViewHolder createViewHolder(View view, FlexibleAdapter<IFlexible> adapter) {
|
||||
return new ConversationItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, ConversationItemViewHolder holder, int position, List<Object> payloads) {
|
||||
Context appContext =
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getApplicationContext();
|
||||
|
||||
holder.dialogAvatar.setController(null);
|
||||
|
||||
if (adapter.hasFilter()) {
|
||||
FlexibleUtils.highlightText(holder.dialogName, conversation.getDisplayName(),
|
||||
String.valueOf(adapter.getFilter(String.class)), NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.colorPrimary));
|
||||
if (!TextUtils.isEmpty(conversation.getLastMessage().getSystemMessage())
|
||||
|| Conversation.ConversationType.ROOM_SYSTEM.equals(conversation.getType())) {
|
||||
holder.dialogLastMessage.setText(conversation.getLastMessage().getText());
|
||||
} else {
|
||||
String authorDisplayName = "";
|
||||
conversation.getLastMessage().setActiveUser(userEntity);
|
||||
String text;
|
||||
if (conversation.getLastMessage()
|
||||
.getMessageType()
|
||||
.equals(ChatMessage.MessageType.REGULAR_TEXT_MESSAGE)) {
|
||||
if (conversation.getLastMessage().getActorId().equals(userEntity.getUserId())) {
|
||||
text = String.format(appContext.getString(R.string.nc_formatted_message_you),
|
||||
conversation.getLastMessage().getLastMessageDisplayText());
|
||||
} else {
|
||||
authorDisplayName =
|
||||
!TextUtils.isEmpty(conversation.getLastMessage().getActorDisplayName()) ?
|
||||
conversation.getLastMessage().getActorDisplayName() :
|
||||
"guests".equals(conversation.getLastMessage().getActorType())
|
||||
? appContext.getString(R.string.nc_guest) : "";
|
||||
text = String.format(appContext.getString(R.string.nc_formatted_message),
|
||||
authorDisplayName,
|
||||
conversation.getLastMessage().getLastMessageDisplayText());
|
||||
}
|
||||
} else {
|
||||
holder.dialogName.setText(conversation.getDisplayName());
|
||||
text = conversation.getLastMessage().getLastMessageDisplayText();
|
||||
}
|
||||
|
||||
if (conversation.getUnreadMessages() > 0) {
|
||||
holder.dialogUnreadBubble.setVisibility(View.VISIBLE);
|
||||
if (conversation.getUnreadMessages() < 100) {
|
||||
holder.dialogUnreadBubble.setText(Long.toString(conversation.getUnreadMessages()));
|
||||
} else {
|
||||
holder.dialogUnreadBubble.setText("99+");
|
||||
}
|
||||
|
||||
if (conversation.isUnreadMention()) {
|
||||
holder.dialogUnreadBubble.setBackground(context.getDrawable(R.drawable.bubble_circle_unread_mention));
|
||||
} else {
|
||||
holder.dialogUnreadBubble.setBackground(context.getDrawable(R.drawable.bubble_circle_unread));
|
||||
}
|
||||
} else {
|
||||
holder.dialogUnreadBubble.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
|
||||
if (conversation.isHasPassword()) {
|
||||
holder.passwordProtectedRoomImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.passwordProtectedRoomImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
if (conversation.isFavorite()) {
|
||||
holder.pinnedConversationImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.pinnedConversationImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
if (conversation.getLastMessage() != null) {
|
||||
holder.dialogDate.setVisibility(View.VISIBLE);
|
||||
holder.dialogDate.setText(DateUtils.getRelativeTimeSpanString(conversation.getLastActivity() * 1000L,
|
||||
System.currentTimeMillis(), 0, DateUtils.FORMAT_ABBREV_RELATIVE));
|
||||
|
||||
if (!TextUtils.isEmpty(conversation.getLastMessage().getSystemMessage()) || Conversation.ConversationType.ROOM_SYSTEM.equals(conversation.getType())) {
|
||||
holder.dialogLastMessage.setText(conversation.getLastMessage().getText());
|
||||
} else {
|
||||
String authorDisplayName = "";
|
||||
conversation.getLastMessage().setActiveUser(userEntity);
|
||||
String text;
|
||||
if (conversation.getLastMessage().getMessageType().equals(ChatMessage.MessageType.REGULAR_TEXT_MESSAGE)) {
|
||||
if (conversation.getLastMessage().getActorId().equals(userEntity.getUserId())) {
|
||||
text = String.format(appContext.getString(R.string.nc_formatted_message_you),
|
||||
conversation.getLastMessage().getLastMessageDisplayText());
|
||||
} else {
|
||||
authorDisplayName = !TextUtils.isEmpty(conversation.getLastMessage().getActorDisplayName()) ?
|
||||
conversation.getLastMessage().getActorDisplayName() :
|
||||
"guests".equals(conversation.getLastMessage().getActorType()) ? appContext.getString(R.string.nc_guest) : "";
|
||||
text = String.format(appContext.getString(R.string.nc_formatted_message),
|
||||
authorDisplayName,
|
||||
conversation.getLastMessage().getLastMessageDisplayText());
|
||||
}
|
||||
} else {
|
||||
text = conversation.getLastMessage().getLastMessageDisplayText();
|
||||
}
|
||||
|
||||
holder.dialogLastMessage.setText(text);
|
||||
}
|
||||
} else {
|
||||
holder.dialogDate.setVisibility(View.GONE);
|
||||
holder.dialogLastMessage.setText(R.string.nc_no_messages_yet);
|
||||
}
|
||||
|
||||
holder.dialogAvatar.setVisibility(View.VISIBLE);
|
||||
|
||||
boolean shouldLoadAvatar = true;
|
||||
String objectType;
|
||||
if (!TextUtils.isEmpty(objectType = conversation.getObjectType())) {
|
||||
switch (objectType) {
|
||||
case "share:password":
|
||||
shouldLoadAvatar = false;
|
||||
holder.dialogAvatar.getHierarchy().setImage(new BitmapDrawable(DisplayUtils
|
||||
.getRoundedBitmapFromVectorDrawableResource(context.getResources(),
|
||||
R.drawable.ic_file_password_request)), 100, true);
|
||||
break;
|
||||
case "file":
|
||||
shouldLoadAvatar = false;
|
||||
holder.dialogAvatar.getHierarchy().setImage(new BitmapDrawable(DisplayUtils
|
||||
.getRoundedBitmapFromVectorDrawableResource(context.getResources(),
|
||||
R.drawable.ic_file_icon)), 100, true);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (Conversation.ConversationType.ROOM_SYSTEM.equals(conversation.getType())) {
|
||||
Drawable[] layers = new Drawable[2];
|
||||
layers[0] = context.getDrawable(R.drawable.ic_launcher_background);
|
||||
layers[1] = context.getDrawable(R.drawable.ic_launcher_foreground);
|
||||
LayerDrawable layerDrawable = new LayerDrawable(layers);
|
||||
|
||||
holder.dialogAvatar.getHierarchy().setPlaceholderImage(DisplayUtils.getRoundedDrawable(layerDrawable));
|
||||
|
||||
shouldLoadAvatar = false;
|
||||
}
|
||||
|
||||
if (shouldLoadAvatar) {
|
||||
switch (conversation.getType()) {
|
||||
case ROOM_TYPE_ONE_TO_ONE_CALL:
|
||||
if (!TextUtils.isEmpty(conversation.getName())) {
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.dialogAvatar.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(ApiUtils.getUrlForAvatarWithName(userEntity.getBaseUrl(), conversation.getName(), R.dimen.avatar_size), null))
|
||||
.build();
|
||||
holder.dialogAvatar.setController(draweeController);
|
||||
} else {
|
||||
holder.dialogAvatar.setVisibility(View.GONE);
|
||||
}
|
||||
break;
|
||||
case ROOM_GROUP_CALL:
|
||||
holder.dialogAvatar.getHierarchy().setImage(new BitmapDrawable(DisplayUtils.getRoundedBitmapFromVectorDrawableResource(context.getResources(), R.drawable.ic_people_group_white_24px)), 100, true);
|
||||
break;
|
||||
case ROOM_PUBLIC_CALL:
|
||||
holder.dialogAvatar.getHierarchy().setImage(new BitmapDrawable(DisplayUtils
|
||||
.getRoundedBitmapFromVectorDrawableResource(context.getResources(),
|
||||
R.drawable.ic_link_white_24px)), 100, true);
|
||||
break;
|
||||
default:
|
||||
holder.dialogAvatar.setVisibility(View.GONE);
|
||||
}
|
||||
}
|
||||
holder.dialogLastMessage.setText(text);
|
||||
}
|
||||
} else {
|
||||
holder.dialogDate.setVisibility(View.GONE);
|
||||
holder.dialogLastMessage.setText(R.string.nc_no_messages_yet);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return conversation.getDisplayName() != null &&
|
||||
Pattern.compile(constraint, Pattern.CASE_INSENSITIVE | Pattern.LITERAL).matcher(conversation.getDisplayName().trim()).find();
|
||||
holder.dialogAvatar.setVisibility(View.VISIBLE);
|
||||
|
||||
boolean shouldLoadAvatar = true;
|
||||
String objectType;
|
||||
if (!TextUtils.isEmpty(objectType = conversation.getObjectType())) {
|
||||
switch (objectType) {
|
||||
case "share:password":
|
||||
shouldLoadAvatar = false;
|
||||
holder.dialogAvatar.getHierarchy().setImage(new BitmapDrawable(DisplayUtils
|
||||
.getRoundedBitmapFromVectorDrawableResource(context.getResources(),
|
||||
R.drawable.ic_file_password_request)), 100, true);
|
||||
break;
|
||||
case "file":
|
||||
shouldLoadAvatar = false;
|
||||
holder.dialogAvatar.getHierarchy().setImage(new BitmapDrawable(DisplayUtils
|
||||
.getRoundedBitmapFromVectorDrawableResource(context.getResources(),
|
||||
R.drawable.ic_file_icon)), 100, true);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static class ConversationItemViewHolder extends FlexibleViewHolder {
|
||||
@BindView(R.id.dialogAvatar)
|
||||
SimpleDraweeView dialogAvatar;
|
||||
@BindView(R.id.dialogName)
|
||||
EmojiTextView dialogName;
|
||||
@BindView(R.id.dialogDate)
|
||||
TextView dialogDate;
|
||||
@BindView(R.id.dialogLastMessage)
|
||||
EmojiTextView dialogLastMessage;
|
||||
@BindView(R.id.dialogUnreadBubble)
|
||||
TextView dialogUnreadBubble;
|
||||
@BindView(R.id.passwordProtectedRoomImageView)
|
||||
ImageView passwordProtectedRoomImageView;
|
||||
@BindView(R.id.favoriteConversationImageView)
|
||||
ImageView pinnedConversationImageView;
|
||||
if (Conversation.ConversationType.ROOM_SYSTEM.equals(conversation.getType())) {
|
||||
Drawable[] layers = new Drawable[2];
|
||||
layers[0] = context.getDrawable(R.drawable.ic_launcher_background);
|
||||
layers[1] = context.getDrawable(R.drawable.ic_launcher_foreground);
|
||||
LayerDrawable layerDrawable = new LayerDrawable(layers);
|
||||
|
||||
ConversationItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
holder.dialogAvatar.getHierarchy()
|
||||
.setPlaceholderImage(DisplayUtils.getRoundedDrawable(layerDrawable));
|
||||
|
||||
shouldLoadAvatar = false;
|
||||
}
|
||||
|
||||
if (shouldLoadAvatar) {
|
||||
switch (conversation.getType()) {
|
||||
case ROOM_TYPE_ONE_TO_ONE_CALL:
|
||||
if (!TextUtils.isEmpty(conversation.getName())) {
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.dialogAvatar.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(
|
||||
ApiUtils.getUrlForAvatarWithName(userEntity.getBaseUrl(),
|
||||
conversation.getName(), R.dimen.avatar_size), null))
|
||||
.build();
|
||||
holder.dialogAvatar.setController(draweeController);
|
||||
} else {
|
||||
holder.dialogAvatar.setVisibility(View.GONE);
|
||||
}
|
||||
break;
|
||||
case ROOM_GROUP_CALL:
|
||||
holder.dialogAvatar.getHierarchy()
|
||||
.setImage(new BitmapDrawable(
|
||||
DisplayUtils.getRoundedBitmapFromVectorDrawableResource(context.getResources(),
|
||||
R.drawable.ic_people_group_white_24px)), 100, true);
|
||||
break;
|
||||
case ROOM_PUBLIC_CALL:
|
||||
holder.dialogAvatar.getHierarchy().setImage(new BitmapDrawable(DisplayUtils
|
||||
.getRoundedBitmapFromVectorDrawableResource(context.getResources(),
|
||||
R.drawable.ic_link_white_24px)), 100, true);
|
||||
break;
|
||||
default:
|
||||
holder.dialogAvatar.setVisibility(View.GONE);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return conversation.getDisplayName() != null &&
|
||||
Pattern.compile(constraint, Pattern.CASE_INSENSITIVE | Pattern.LITERAL)
|
||||
.matcher(conversation.getDisplayName().trim())
|
||||
.find();
|
||||
}
|
||||
|
||||
static class ConversationItemViewHolder extends FlexibleViewHolder {
|
||||
@BindView(R.id.dialogAvatar)
|
||||
SimpleDraweeView dialogAvatar;
|
||||
@BindView(R.id.dialogName)
|
||||
EmojiTextView dialogName;
|
||||
@BindView(R.id.dialogDate)
|
||||
TextView dialogDate;
|
||||
@BindView(R.id.dialogLastMessage)
|
||||
EmojiTextView dialogLastMessage;
|
||||
@BindView(R.id.dialogUnreadBubble)
|
||||
TextView dialogUnreadBubble;
|
||||
@BindView(R.id.passwordProtectedRoomImageView)
|
||||
ImageView passwordProtectedRoomImageView;
|
||||
@BindView(R.id.favoriteConversationImageView)
|
||||
ImageView pinnedConversationImageView;
|
||||
|
||||
ConversationItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -32,63 +32,63 @@ import eu.davidea.flexibleadapter.items.IFlexible;
|
||||
import eu.davidea.viewholders.FlexibleViewHolder;
|
||||
import java.util.List;
|
||||
|
||||
public class GenericTextHeaderItem extends AbstractHeaderItem<GenericTextHeaderItem.HeaderViewHolder> {
|
||||
private static final String TAG = "GenericTextHeaderItem";
|
||||
public class GenericTextHeaderItem
|
||||
extends AbstractHeaderItem<GenericTextHeaderItem.HeaderViewHolder> {
|
||||
private static final String TAG = "GenericTextHeaderItem";
|
||||
|
||||
private String title;
|
||||
private String title;
|
||||
|
||||
public GenericTextHeaderItem(String title) {
|
||||
super();
|
||||
setHidden(false);
|
||||
setSelectable(false);
|
||||
this.title = title;
|
||||
public GenericTextHeaderItem(String title) {
|
||||
super();
|
||||
setHidden(false);
|
||||
setSelectable(false);
|
||||
this.title = title;
|
||||
}
|
||||
|
||||
public String getModel() {
|
||||
return title;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof GenericTextHeaderItem) {
|
||||
GenericTextHeaderItem inItem = (GenericTextHeaderItem) o;
|
||||
return title.equals(inItem.getModel());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public String getModel() {
|
||||
return title;
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_title_header;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, HeaderViewHolder holder,
|
||||
int position, List<Object> payloads) {
|
||||
if (payloads.size() > 0) {
|
||||
Log.d(TAG, "We have payloads, so ignoring!");
|
||||
} else {
|
||||
holder.titleTextView.setText(title);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof GenericTextHeaderItem) {
|
||||
GenericTextHeaderItem inItem = (GenericTextHeaderItem) o;
|
||||
return title.equals(inItem.getModel());
|
||||
}
|
||||
return false;
|
||||
@Override
|
||||
public HeaderViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new HeaderViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
static class HeaderViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.title_text_view)
|
||||
public TextView titleTextView;
|
||||
|
||||
/**
|
||||
* Default constructor.
|
||||
*/
|
||||
HeaderViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter, true);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_title_header;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, HeaderViewHolder holder, int position, List<Object> payloads) {
|
||||
if (payloads.size() > 0) {
|
||||
Log.d(TAG, "We have payloads, so ignoring!");
|
||||
} else {
|
||||
holder.titleTextView.setText(title);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public HeaderViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new HeaderViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
static class HeaderViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.title_text_view)
|
||||
public TextView titleTextView;
|
||||
|
||||
/**
|
||||
* Default constructor.
|
||||
*/
|
||||
HeaderViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter, true);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -38,103 +38,112 @@ import java.util.List;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
public class MentionAutocompleteItem extends AbstractFlexibleItem<UserItem.UserItemViewHolder>
|
||||
implements IFilterable<String> {
|
||||
implements IFilterable<String> {
|
||||
|
||||
private String objectId;
|
||||
private String displayName;
|
||||
private String source;
|
||||
private UserEntity currentUser;
|
||||
private String objectId;
|
||||
private String displayName;
|
||||
private String source;
|
||||
private UserEntity currentUser;
|
||||
|
||||
public MentionAutocompleteItem(String objectId, String displayName, String source, UserEntity currentUser) {
|
||||
this.objectId = objectId;
|
||||
this.displayName = displayName;
|
||||
this.source = source;
|
||||
this.currentUser = currentUser;
|
||||
public MentionAutocompleteItem(String objectId, String displayName, String source,
|
||||
UserEntity currentUser) {
|
||||
this.objectId = objectId;
|
||||
this.displayName = displayName;
|
||||
this.source = source;
|
||||
this.currentUser = currentUser;
|
||||
}
|
||||
|
||||
public String getSource() {
|
||||
return source;
|
||||
}
|
||||
|
||||
public void setSource(String source) {
|
||||
this.source = source;
|
||||
}
|
||||
|
||||
public String getObjectId() {
|
||||
return objectId;
|
||||
}
|
||||
|
||||
public String getDisplayName() {
|
||||
return displayName;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof MentionAutocompleteItem) {
|
||||
MentionAutocompleteItem inItem = (MentionAutocompleteItem) o;
|
||||
return (objectId.equals(inItem.objectId) && displayName.equals(inItem.displayName));
|
||||
}
|
||||
|
||||
public String getSource() {
|
||||
return source;
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_mention;
|
||||
}
|
||||
|
||||
@Override
|
||||
public UserItem.UserItemViewHolder createViewHolder(View view,
|
||||
FlexibleAdapter<IFlexible> adapter) {
|
||||
return new UserItem.UserItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@SuppressLint("SetTextI18n")
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, UserItem.UserItemViewHolder holder,
|
||||
int position, List<Object> payloads) {
|
||||
|
||||
if (adapter.hasFilter()) {
|
||||
FlexibleUtils.highlightText(holder.contactDisplayName, displayName,
|
||||
String.valueOf(adapter.getFilter(String.class)),
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.colorPrimary));
|
||||
if (holder.contactMentionId != null) {
|
||||
FlexibleUtils.highlightText(holder.contactMentionId, "@" + objectId,
|
||||
String.valueOf(adapter.getFilter(String.class)),
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.colorPrimary));
|
||||
}
|
||||
} else {
|
||||
holder.contactDisplayName.setText(displayName);
|
||||
if (holder.contactMentionId != null) {
|
||||
holder.contactMentionId.setText("@" + objectId);
|
||||
}
|
||||
}
|
||||
|
||||
public void setSource(String source) {
|
||||
this.source = source;
|
||||
if (source.equals("calls")) {
|
||||
holder.simpleDraweeView.getHierarchy()
|
||||
.setPlaceholderImage(DisplayUtils.getRoundedBitmapDrawableFromVectorDrawableResource(
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getResources(),
|
||||
R.drawable.ic_people_group_white_24px));
|
||||
} else {
|
||||
String avatarId = objectId;
|
||||
String avatarUrl = ApiUtils.getUrlForAvatarWithName(currentUser.getBaseUrl(),
|
||||
avatarId, R.dimen.avatar_size_big);
|
||||
|
||||
if (source.equals("guests")) {
|
||||
avatarId = displayName;
|
||||
avatarUrl = ApiUtils.getUrlForAvatarWithNameForGuests(currentUser.getBaseUrl(), avatarId,
|
||||
R.dimen.avatar_size_big);
|
||||
}
|
||||
|
||||
holder.simpleDraweeView.setController(null);
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.simpleDraweeView.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(avatarUrl, null))
|
||||
.build();
|
||||
holder.simpleDraweeView.setController(draweeController);
|
||||
}
|
||||
}
|
||||
|
||||
public String getObjectId() {
|
||||
return objectId;
|
||||
}
|
||||
|
||||
public String getDisplayName() {
|
||||
return displayName;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof MentionAutocompleteItem) {
|
||||
MentionAutocompleteItem inItem = (MentionAutocompleteItem) o;
|
||||
return (objectId.equals(inItem.objectId) && displayName.equals(inItem.displayName));
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_mention;
|
||||
}
|
||||
|
||||
@Override
|
||||
public UserItem.UserItemViewHolder createViewHolder(View view, FlexibleAdapter<IFlexible> adapter) {
|
||||
return new UserItem.UserItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
|
||||
@SuppressLint("SetTextI18n")
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, UserItem.UserItemViewHolder holder, int position, List<Object> payloads) {
|
||||
|
||||
if (adapter.hasFilter()) {
|
||||
FlexibleUtils.highlightText(holder.contactDisplayName, displayName,
|
||||
String.valueOf(adapter.getFilter(String.class)), NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.colorPrimary));
|
||||
if (holder.contactMentionId != null) {
|
||||
FlexibleUtils.highlightText(holder.contactMentionId, "@" + objectId,
|
||||
String.valueOf(adapter.getFilter(String.class)), NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.colorPrimary));
|
||||
}
|
||||
} else {
|
||||
holder.contactDisplayName.setText(displayName);
|
||||
if (holder.contactMentionId != null) {
|
||||
holder.contactMentionId.setText("@" + objectId);
|
||||
}
|
||||
}
|
||||
|
||||
if (source.equals("calls")) {
|
||||
holder.simpleDraweeView.getHierarchy().setPlaceholderImage(DisplayUtils.getRoundedBitmapDrawableFromVectorDrawableResource(NextcloudTalkApplication.Companion.getSharedApplication().getResources(), R.drawable.ic_people_group_white_24px));
|
||||
} else {
|
||||
String avatarId = objectId;
|
||||
String avatarUrl = ApiUtils.getUrlForAvatarWithName(currentUser.getBaseUrl(),
|
||||
avatarId, R.dimen.avatar_size_big);
|
||||
|
||||
if (source.equals("guests")) {
|
||||
avatarId = displayName;
|
||||
avatarUrl = ApiUtils.getUrlForAvatarWithNameForGuests(currentUser.getBaseUrl(), avatarId, R.dimen.avatar_size_big);
|
||||
}
|
||||
|
||||
holder.simpleDraweeView.setController(null);
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.simpleDraweeView.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(avatarUrl, null))
|
||||
.build();
|
||||
holder.simpleDraweeView.setController(draweeController);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return objectId != null && Pattern.compile(constraint,
|
||||
Pattern.CASE_INSENSITIVE | Pattern.LITERAL).matcher(objectId).find()
|
||||
|| displayName != null && Pattern.compile(constraint, Pattern.CASE_INSENSITIVE | Pattern.LITERAL).matcher(displayName).find();
|
||||
}
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return objectId != null && Pattern.compile(constraint,
|
||||
Pattern.CASE_INSENSITIVE | Pattern.LITERAL).matcher(objectId).find()
|
||||
|| displayName != null && Pattern.compile(constraint,
|
||||
Pattern.CASE_INSENSITIVE | Pattern.LITERAL).matcher(displayName).find();
|
||||
}
|
||||
}
|
||||
|
@ -39,69 +39,71 @@ import eu.davidea.viewholders.FlexibleViewHolder;
|
||||
import java.util.List;
|
||||
|
||||
public class MenuItem extends AbstractFlexibleItem<MenuItem.MenuItemViewHolder> {
|
||||
private String title;
|
||||
private Drawable icon;
|
||||
private int tag;
|
||||
private int padding;
|
||||
private String title;
|
||||
private Drawable icon;
|
||||
private int tag;
|
||||
private int padding;
|
||||
|
||||
public MenuItem(String title, int tag, Drawable icon) {
|
||||
this.title = title;
|
||||
this.tag = tag;
|
||||
this.icon = icon;
|
||||
padding = (int) DisplayUtils.convertDpToPixel(16,
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getApplicationContext());
|
||||
public MenuItem(String title, int tag, Drawable icon) {
|
||||
this.title = title;
|
||||
this.tag = tag;
|
||||
this.icon = icon;
|
||||
padding = (int) DisplayUtils.convertDpToPixel(16,
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getApplicationContext());
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof MenuItem) {
|
||||
MenuItem inItem = (MenuItem) o;
|
||||
return tag == inItem.tag;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof MenuItem) {
|
||||
MenuItem inItem = (MenuItem) o;
|
||||
return tag == inItem.tag;
|
||||
}
|
||||
return false;
|
||||
public int getTag() {
|
||||
return tag;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_menu;
|
||||
}
|
||||
|
||||
@Override
|
||||
public MenuItem.MenuItemViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new MenuItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter adapter, MenuItem.MenuItemViewHolder holder,
|
||||
int position, List payloads) {
|
||||
if (position == 0) {
|
||||
Spannable spannableString = new SpannableString(title);
|
||||
spannableString.setSpan(
|
||||
new ForegroundColorSpan(NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.grey_600)), 0,
|
||||
spannableString.length(),
|
||||
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
|
||||
holder.menuTitle.setText(spannableString);
|
||||
} else {
|
||||
holder.menuTitle.setText(title);
|
||||
holder.menuTitle.setCompoundDrawablesWithIntrinsicBounds(icon, null, null, null);
|
||||
holder.menuTitle.setCompoundDrawablePadding(padding);
|
||||
}
|
||||
}
|
||||
|
||||
public int getTag() {
|
||||
return tag;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_menu;
|
||||
}
|
||||
|
||||
@Override
|
||||
public MenuItem.MenuItemViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new MenuItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter adapter, MenuItem.MenuItemViewHolder holder, int position, List payloads) {
|
||||
if (position == 0) {
|
||||
Spannable spannableString = new SpannableString(title);
|
||||
spannableString.setSpan(new ForegroundColorSpan(NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources().getColor(R.color.grey_600)), 0,
|
||||
spannableString.length(),
|
||||
Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
|
||||
holder.menuTitle.setText(spannableString);
|
||||
} else {
|
||||
holder.menuTitle.setText(title);
|
||||
holder.menuTitle.setCompoundDrawablesWithIntrinsicBounds(icon, null, null, null);
|
||||
holder.menuTitle.setCompoundDrawablePadding(padding);
|
||||
}
|
||||
}
|
||||
|
||||
static class MenuItemViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.menu_text)
|
||||
public TextView menuTitle;
|
||||
|
||||
/**
|
||||
* Default constructor.
|
||||
*/
|
||||
MenuItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
static class MenuItemViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.menu_text)
|
||||
public TextView menuTitle;
|
||||
|
||||
/**
|
||||
* Default constructor.
|
||||
*/
|
||||
MenuItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -36,76 +36,80 @@ import eu.davidea.flexibleadapter.items.IFlexible;
|
||||
import eu.davidea.viewholders.FlexibleViewHolder;
|
||||
import java.util.List;
|
||||
|
||||
public class NotificationSoundItem extends AbstractFlexibleItem<NotificationSoundItem.NotificationSoundItemViewHolder> {
|
||||
public class NotificationSoundItem
|
||||
extends AbstractFlexibleItem<NotificationSoundItem.NotificationSoundItemViewHolder> {
|
||||
|
||||
private String notificationSoundName;
|
||||
private String notificationSoundUri;
|
||||
private String notificationSoundName;
|
||||
private String notificationSoundUri;
|
||||
|
||||
public NotificationSoundItem(String notificationSoundName, String notificationSoundUri) {
|
||||
this.notificationSoundName = notificationSoundName;
|
||||
this.notificationSoundUri = notificationSoundUri;
|
||||
public NotificationSoundItem(String notificationSoundName, String notificationSoundUri) {
|
||||
this.notificationSoundName = notificationSoundName;
|
||||
this.notificationSoundUri = notificationSoundUri;
|
||||
}
|
||||
|
||||
public String getNotificationSoundUri() {
|
||||
return notificationSoundUri;
|
||||
}
|
||||
|
||||
public String getNotificationSoundName() {
|
||||
return notificationSoundName;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_notification_sound;
|
||||
}
|
||||
|
||||
@Override
|
||||
public NotificationSoundItemViewHolder createViewHolder(View view,
|
||||
FlexibleAdapter<IFlexible> adapter) {
|
||||
return new NotificationSoundItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter,
|
||||
NotificationSoundItemViewHolder holder, int position, List<Object> payloads) {
|
||||
holder.notificationName.setText(notificationSoundName);
|
||||
|
||||
if (adapter.isSelected(position)) {
|
||||
holder.checkedImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.checkedImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
public String getNotificationSoundUri() {
|
||||
return notificationSoundUri;
|
||||
Resources resources = NextcloudTalkApplication.Companion.getSharedApplication().getResources();
|
||||
holder.simpleDraweeView.getHierarchy()
|
||||
.setBackgroundImage(new ColorDrawable(resources.getColor(R.color.colorPrimary)));
|
||||
if (position == 0) {
|
||||
holder.simpleDraweeView.getHierarchy()
|
||||
.setImage(resources.getDrawable(R.drawable.ic_stop_white_24dp), 100,
|
||||
true);
|
||||
} else {
|
||||
holder.simpleDraweeView.getHierarchy()
|
||||
.setImage(resources.getDrawable(R.drawable.ic_play_circle_outline_white_24dp), 100,
|
||||
true);
|
||||
}
|
||||
}
|
||||
|
||||
public String getNotificationSoundName() {
|
||||
return notificationSoundName;
|
||||
static class NotificationSoundItemViewHolder extends FlexibleViewHolder {
|
||||
@BindView(R.id.notificationNameTextView)
|
||||
public TextView notificationName;
|
||||
@BindView(R.id.simpleDraweeView)
|
||||
SimpleDraweeView simpleDraweeView;
|
||||
@BindView(R.id.checkedImageView)
|
||||
ImageView checkedImageView;
|
||||
|
||||
/**
|
||||
* Default constructor.
|
||||
*/
|
||||
NotificationSoundItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_notification_sound;
|
||||
}
|
||||
|
||||
@Override
|
||||
public NotificationSoundItemViewHolder createViewHolder(View view, FlexibleAdapter<IFlexible> adapter) {
|
||||
return new NotificationSoundItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, NotificationSoundItemViewHolder holder, int position, List<Object> payloads) {
|
||||
holder.notificationName.setText(notificationSoundName);
|
||||
|
||||
if (adapter.isSelected(position)) {
|
||||
holder.checkedImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.checkedImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
Resources resources = NextcloudTalkApplication.Companion.getSharedApplication().getResources();
|
||||
holder.simpleDraweeView.getHierarchy().setBackgroundImage(new ColorDrawable(resources.getColor(R.color.colorPrimary)));
|
||||
if (position == 0) {
|
||||
holder.simpleDraweeView.getHierarchy().setImage(resources.getDrawable(R.drawable.ic_stop_white_24dp), 100,
|
||||
true);
|
||||
} else {
|
||||
holder.simpleDraweeView.getHierarchy().setImage(resources.getDrawable(R.drawable.ic_play_circle_outline_white_24dp), 100,
|
||||
true);
|
||||
}
|
||||
}
|
||||
|
||||
static class NotificationSoundItemViewHolder extends FlexibleViewHolder {
|
||||
@BindView(R.id.notificationNameTextView)
|
||||
public TextView notificationName;
|
||||
@BindView(R.id.simpleDraweeView)
|
||||
SimpleDraweeView simpleDraweeView;
|
||||
@BindView(R.id.checkedImageView)
|
||||
ImageView checkedImageView;
|
||||
|
||||
/**
|
||||
* Default constructor.
|
||||
*/
|
||||
NotificationSoundItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -47,95 +47,95 @@ import java.util.List;
|
||||
*/
|
||||
public class ProgressItem extends AbstractFlexibleItem<ProgressItem.ProgressViewHolder> {
|
||||
|
||||
private StatusEnum status = StatusEnum.MORE_TO_LOAD;
|
||||
private StatusEnum status = StatusEnum.MORE_TO_LOAD;
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
return this == o;//The default implementation
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
return this == o;//The default implementation
|
||||
}
|
||||
|
||||
public StatusEnum getStatus() {
|
||||
return status;
|
||||
}
|
||||
|
||||
public void setStatus(StatusEnum status) {
|
||||
this.status = status;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_progress;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, ProgressViewHolder holder,
|
||||
int position, List<Object> payloads) {
|
||||
Context context = holder.itemView.getContext();
|
||||
holder.progressBar.setVisibility(View.GONE);
|
||||
holder.progressMessage.setVisibility(View.VISIBLE);
|
||||
|
||||
if (!adapter.isEndlessScrollEnabled()) {
|
||||
setStatus(StatusEnum.DISABLE_ENDLESS);
|
||||
} else if (payloads.contains(Payload.NO_MORE_LOAD)) {
|
||||
setStatus(StatusEnum.NO_MORE_LOAD);
|
||||
}
|
||||
|
||||
public StatusEnum getStatus() {
|
||||
return status;
|
||||
switch (this.status) {
|
||||
case NO_MORE_LOAD:
|
||||
holder.progressMessage.setText(
|
||||
context.getString(R.string.nc_no_more_load_retry));
|
||||
// Reset to default status for next binding
|
||||
setStatus(StatusEnum.MORE_TO_LOAD);
|
||||
break;
|
||||
case DISABLE_ENDLESS:
|
||||
holder.progressMessage.setText(context.getString(R.string.nc_endless_disabled));
|
||||
break;
|
||||
case ON_CANCEL:
|
||||
holder.progressMessage.setText(context.getString(R.string.nc_endless_cancel));
|
||||
// Reset to default status for next binding
|
||||
setStatus(StatusEnum.MORE_TO_LOAD);
|
||||
break;
|
||||
case ON_ERROR:
|
||||
holder.progressMessage.setText(context.getString(R.string.nc_endless_error));
|
||||
// Reset to default status for next binding
|
||||
setStatus(StatusEnum.MORE_TO_LOAD);
|
||||
break;
|
||||
default:
|
||||
holder.progressBar.setVisibility(View.VISIBLE);
|
||||
holder.progressMessage.setVisibility(View.GONE);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
public void setStatus(StatusEnum status) {
|
||||
this.status = status;
|
||||
@Override
|
||||
public ProgressViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new ProgressViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
public enum StatusEnum {
|
||||
MORE_TO_LOAD, //Default = should have an empty Payload
|
||||
DISABLE_ENDLESS, //Endless is disabled because user has set limits
|
||||
NO_MORE_LOAD, //Non-empty Payload = Payload.NO_MORE_LOAD
|
||||
ON_CANCEL,
|
||||
ON_ERROR
|
||||
}
|
||||
|
||||
static class ProgressViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.progress_bar)
|
||||
ProgressBar progressBar;
|
||||
@BindView(R.id.progress_message)
|
||||
TextView progressMessage;
|
||||
|
||||
ProgressViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_progress;
|
||||
public void scrollAnimators(@NonNull List<Animator> animators, int position,
|
||||
boolean isForward) {
|
||||
AnimatorHelper.scaleAnimator(animators, itemView, 0f);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, ProgressViewHolder holder, int position, List<Object> payloads) {
|
||||
Context context = holder.itemView.getContext();
|
||||
holder.progressBar.setVisibility(View.GONE);
|
||||
holder.progressMessage.setVisibility(View.VISIBLE);
|
||||
|
||||
if (!adapter.isEndlessScrollEnabled()) {
|
||||
setStatus(StatusEnum.DISABLE_ENDLESS);
|
||||
} else if (payloads.contains(Payload.NO_MORE_LOAD)) {
|
||||
setStatus(StatusEnum.NO_MORE_LOAD);
|
||||
}
|
||||
|
||||
switch (this.status) {
|
||||
case NO_MORE_LOAD:
|
||||
holder.progressMessage.setText(
|
||||
context.getString(R.string.nc_no_more_load_retry));
|
||||
// Reset to default status for next binding
|
||||
setStatus(StatusEnum.MORE_TO_LOAD);
|
||||
break;
|
||||
case DISABLE_ENDLESS:
|
||||
holder.progressMessage.setText(context.getString(R.string.nc_endless_disabled));
|
||||
break;
|
||||
case ON_CANCEL:
|
||||
holder.progressMessage.setText(context.getString(R.string.nc_endless_cancel));
|
||||
// Reset to default status for next binding
|
||||
setStatus(StatusEnum.MORE_TO_LOAD);
|
||||
break;
|
||||
case ON_ERROR:
|
||||
holder.progressMessage.setText(context.getString(R.string.nc_endless_error));
|
||||
// Reset to default status for next binding
|
||||
setStatus(StatusEnum.MORE_TO_LOAD);
|
||||
break;
|
||||
default:
|
||||
holder.progressBar.setVisibility(View.VISIBLE);
|
||||
holder.progressMessage.setVisibility(View.GONE);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public ProgressViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new ProgressViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
|
||||
public enum StatusEnum {
|
||||
MORE_TO_LOAD, //Default = should have an empty Payload
|
||||
DISABLE_ENDLESS, //Endless is disabled because user has set limits
|
||||
NO_MORE_LOAD, //Non-empty Payload = Payload.NO_MORE_LOAD
|
||||
ON_CANCEL,
|
||||
ON_ERROR
|
||||
}
|
||||
|
||||
static class ProgressViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.progress_bar)
|
||||
ProgressBar progressBar;
|
||||
@BindView(R.id.progress_message)
|
||||
TextView progressMessage;
|
||||
|
||||
ProgressViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void scrollAnimators(@NonNull List<Animator> animators, int position, boolean isForward) {
|
||||
AnimatorHelper.scaleAnimator(animators, itemView, 0f);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -50,248 +50,266 @@ import java.util.regex.Pattern;
|
||||
import javax.annotation.Nullable;
|
||||
|
||||
public class UserItem extends AbstractFlexibleItem<UserItem.UserItemViewHolder> implements
|
||||
ISectionable<UserItem.UserItemViewHolder, GenericTextHeaderItem>, IFilterable<String> {
|
||||
ISectionable<UserItem.UserItemViewHolder, GenericTextHeaderItem>, IFilterable<String> {
|
||||
|
||||
private Participant participant;
|
||||
private UserEntity userEntity;
|
||||
private GenericTextHeaderItem header;
|
||||
private Context activityContext;
|
||||
public boolean isOnline = true;
|
||||
public boolean isOnline = true;
|
||||
private Participant participant;
|
||||
private UserEntity userEntity;
|
||||
private GenericTextHeaderItem header;
|
||||
private Context activityContext;
|
||||
|
||||
public UserItem(Participant participant, UserEntity userEntity,
|
||||
GenericTextHeaderItem genericTextHeaderItem, Context activityContext) {
|
||||
this.participant = participant;
|
||||
this.userEntity = userEntity;
|
||||
this.header = genericTextHeaderItem;
|
||||
this.activityContext = activityContext;
|
||||
public UserItem(Participant participant, UserEntity userEntity,
|
||||
GenericTextHeaderItem genericTextHeaderItem, Context activityContext) {
|
||||
this.participant = participant;
|
||||
this.userEntity = userEntity;
|
||||
this.header = genericTextHeaderItem;
|
||||
this.activityContext = activityContext;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof UserItem) {
|
||||
UserItem inItem = (UserItem) o;
|
||||
return participant.getUserId().equals(inItem.getModel().getUserId());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return participant.hashCode();
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the model object
|
||||
*/
|
||||
|
||||
public Participant getModel() {
|
||||
return participant;
|
||||
}
|
||||
|
||||
public UserEntity getEntity() {
|
||||
return userEntity;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
if (header != null) {
|
||||
return R.layout.rv_item_contact;
|
||||
} else {
|
||||
return R.layout.rv_item_conversation_info_participant;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public UserItemViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new UserItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter adapter, UserItemViewHolder holder, int position,
|
||||
List payloads) {
|
||||
|
||||
holder.simpleDraweeView.setController(null);
|
||||
|
||||
if (holder.checkedImageView != null) {
|
||||
if (participant.isSelected()) {
|
||||
holder.checkedImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.checkedImageView.setVisibility(View.GONE);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof UserItem) {
|
||||
UserItem inItem = (UserItem) o;
|
||||
return participant.getUserId().equals(inItem.getModel().getUserId());
|
||||
if (!isOnline) {
|
||||
if (holder.contactMentionId != null) {
|
||||
holder.contactMentionId.setAlpha(0.38f);
|
||||
}
|
||||
holder.contactDisplayName.setAlpha(0.38f);
|
||||
holder.simpleDraweeView.setAlpha(0.38f);
|
||||
} else {
|
||||
if (holder.contactMentionId != null) {
|
||||
holder.contactMentionId.setAlpha(1.0f);
|
||||
}
|
||||
holder.contactDisplayName.setAlpha(1.0f);
|
||||
holder.simpleDraweeView.setAlpha(1.0f);
|
||||
}
|
||||
|
||||
if (adapter.hasFilter()) {
|
||||
FlexibleUtils.highlightText(holder.contactDisplayName, participant.getDisplayName(),
|
||||
String.valueOf(adapter.getFilter(String.class)),
|
||||
activityContext.getResources().getColor(R.color.colorPrimary));
|
||||
}
|
||||
|
||||
holder.contactDisplayName.setText(participant.getDisplayName());
|
||||
|
||||
if (TextUtils.isEmpty(participant.getDisplayName()) &&
|
||||
(participant.getType().equals(Participant.ParticipantType.GUEST) || participant.getType()
|
||||
.equals(Participant.ParticipantType.USER_FOLLOWING_LINK))) {
|
||||
holder.contactDisplayName.setText(
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_guest));
|
||||
}
|
||||
|
||||
if (TextUtils.isEmpty(participant.getSource()) || participant.getSource().equals("users")) {
|
||||
if (Participant.ParticipantType.GUEST.equals(participant.getType()) ||
|
||||
Participant.ParticipantType.USER_FOLLOWING_LINK.equals(participant.getType())) {
|
||||
String displayName = NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources()
|
||||
.getString(R.string.nc_guest);
|
||||
|
||||
if (!TextUtils.isEmpty(participant.getDisplayName())) {
|
||||
displayName = participant.getDisplayName();
|
||||
}
|
||||
return false;
|
||||
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.simpleDraweeView.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(
|
||||
ApiUtils.getUrlForAvatarWithNameForGuests(userEntity.getBaseUrl(),
|
||||
displayName, R.dimen.avatar_size), null))
|
||||
.build();
|
||||
holder.simpleDraweeView.setController(draweeController);
|
||||
} else {
|
||||
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.simpleDraweeView.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(
|
||||
ApiUtils.getUrlForAvatarWithName(userEntity.getBaseUrl(),
|
||||
participant.getUserId(), R.dimen.avatar_size), null))
|
||||
.build();
|
||||
holder.simpleDraweeView.setController(draweeController);
|
||||
}
|
||||
} else if ("groups".equals(participant.getSource())) {
|
||||
holder.simpleDraweeView.getHierarchy()
|
||||
.setImage(new BitmapDrawable(DisplayUtils.getRoundedBitmapFromVectorDrawableResource(
|
||||
activityContext.getResources(), R.drawable.ic_people_group_white_24px)), 100, true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return participant.hashCode();
|
||||
Resources resources = activityContext.getResources();
|
||||
|
||||
if (header == null) {
|
||||
Participant.ParticipantFlags participantFlags = participant.getParticipantFlags();
|
||||
switch (participantFlags) {
|
||||
case NOT_IN_CALL:
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.GONE);
|
||||
holder.videoCallImageView.setVisibility(View.GONE);
|
||||
break;
|
||||
case IN_CALL:
|
||||
holder.voiceOrSimpleCallImageView.setBackground(
|
||||
resources.getDrawable(R.drawable.shape_call_bubble));
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.VISIBLE);
|
||||
holder.videoCallImageView.setVisibility(View.GONE);
|
||||
break;
|
||||
case IN_CALL_WITH_AUDIO:
|
||||
holder.voiceOrSimpleCallImageView.setBackground(
|
||||
resources.getDrawable(R.drawable.shape_voice_bubble));
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.VISIBLE);
|
||||
holder.videoCallImageView.setVisibility(View.GONE);
|
||||
break;
|
||||
case IN_CALL_WITH_VIDEO:
|
||||
holder.voiceOrSimpleCallImageView.setBackground(
|
||||
resources.getDrawable(R.drawable.shape_call_bubble));
|
||||
holder.videoCallImageView.setBackground(
|
||||
resources.getDrawable(R.drawable.shape_video_bubble));
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.VISIBLE);
|
||||
holder.videoCallImageView.setVisibility(View.VISIBLE);
|
||||
break;
|
||||
case IN_CALL_WITH_AUDIO_AND_VIDEO:
|
||||
holder.voiceOrSimpleCallImageView.setBackground(
|
||||
resources.getDrawable(R.drawable.shape_voice_bubble));
|
||||
holder.videoCallImageView.setBackground(
|
||||
resources.getDrawable(R.drawable.shape_video_bubble));
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.VISIBLE);
|
||||
holder.videoCallImageView.setVisibility(View.VISIBLE);
|
||||
break;
|
||||
default:
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.GONE);
|
||||
holder.videoCallImageView.setVisibility(View.GONE);
|
||||
break;
|
||||
}
|
||||
|
||||
if (holder.contactMentionId != null) {
|
||||
String userType = "";
|
||||
|
||||
switch (new EnumParticipantTypeConverter().convertToInt(participant.getType())) {
|
||||
case 1:
|
||||
//userType = NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_owner);
|
||||
//break;
|
||||
case 2:
|
||||
userType = NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_moderator);
|
||||
break;
|
||||
case 3:
|
||||
userType = NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_user);
|
||||
break;
|
||||
case 4:
|
||||
userType = NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_guest);
|
||||
break;
|
||||
case 5:
|
||||
userType = NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_following_link);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
if (!holder.contactMentionId.getText().equals(userType)) {
|
||||
holder.contactMentionId.setText(userType);
|
||||
holder.contactMentionId.setTextColor(
|
||||
activityContext.getResources().getColor(R.color.colorPrimary));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return participant.getDisplayName() != null &&
|
||||
(Pattern.compile(constraint, Pattern.CASE_INSENSITIVE | Pattern.LITERAL)
|
||||
.matcher(participant.getDisplayName().trim())
|
||||
.find() ||
|
||||
Pattern.compile(constraint, Pattern.CASE_INSENSITIVE | Pattern.LITERAL)
|
||||
.matcher(participant.getUserId().trim())
|
||||
.find());
|
||||
}
|
||||
|
||||
@Override
|
||||
public GenericTextHeaderItem getHeader() {
|
||||
return header;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setHeader(GenericTextHeaderItem header) {
|
||||
this.header = header;
|
||||
}
|
||||
|
||||
static class UserItemViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.name_text)
|
||||
public EmojiTextView contactDisplayName;
|
||||
@BindView(R.id.simple_drawee_view)
|
||||
public SimpleDraweeView simpleDraweeView;
|
||||
@Nullable
|
||||
@BindView(R.id.secondary_text)
|
||||
public EmojiTextView contactMentionId;
|
||||
@Nullable
|
||||
@BindView(R.id.voiceOrSimpleCallImageView)
|
||||
ImageView voiceOrSimpleCallImageView;
|
||||
@Nullable
|
||||
@BindView(R.id.videoCallImageView)
|
||||
ImageView videoCallImageView;
|
||||
@Nullable
|
||||
@BindView(R.id.checkedImageView)
|
||||
ImageView checkedImageView;
|
||||
|
||||
/**
|
||||
* @return the model object
|
||||
* Default constructor.
|
||||
*/
|
||||
|
||||
public Participant getModel() {
|
||||
return participant;
|
||||
UserItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
|
||||
public UserEntity getEntity() {
|
||||
return userEntity;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
if (header != null) {
|
||||
return R.layout.rv_item_contact;
|
||||
} else {
|
||||
return R.layout.rv_item_conversation_info_participant;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public UserItemViewHolder createViewHolder(View view, FlexibleAdapter adapter) {
|
||||
return new UserItemViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter adapter, UserItemViewHolder holder, int position, List payloads) {
|
||||
|
||||
holder.simpleDraweeView.setController(null);
|
||||
|
||||
if (holder.checkedImageView != null) {
|
||||
if (participant.isSelected()) {
|
||||
holder.checkedImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.checkedImageView.setVisibility(View.GONE);
|
||||
}
|
||||
}
|
||||
|
||||
if (!isOnline) {
|
||||
if (holder.contactMentionId != null) {
|
||||
holder.contactMentionId.setAlpha(0.38f);
|
||||
}
|
||||
holder.contactDisplayName.setAlpha(0.38f);
|
||||
holder.simpleDraweeView.setAlpha(0.38f);
|
||||
} else {
|
||||
if (holder.contactMentionId != null) {
|
||||
holder.contactMentionId.setAlpha(1.0f);
|
||||
}
|
||||
holder.contactDisplayName.setAlpha(1.0f);
|
||||
holder.simpleDraweeView.setAlpha(1.0f);
|
||||
}
|
||||
|
||||
if (adapter.hasFilter()) {
|
||||
FlexibleUtils.highlightText(holder.contactDisplayName, participant.getDisplayName(),
|
||||
String.valueOf(adapter.getFilter(String.class)), activityContext.getResources().getColor(R.color.colorPrimary));
|
||||
}
|
||||
|
||||
holder.contactDisplayName.setText(participant.getDisplayName());
|
||||
|
||||
if (TextUtils.isEmpty(participant.getDisplayName()) &&
|
||||
(participant.getType().equals(Participant.ParticipantType.GUEST) || participant.getType().equals(Participant.ParticipantType.USER_FOLLOWING_LINK))) {
|
||||
holder.contactDisplayName.setText(NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_guest));
|
||||
}
|
||||
|
||||
if (TextUtils.isEmpty(participant.getSource()) || participant.getSource().equals("users")) {
|
||||
if (Participant.ParticipantType.GUEST.equals(participant.getType()) ||
|
||||
Participant.ParticipantType.USER_FOLLOWING_LINK.equals(participant.getType())) {
|
||||
String displayName = NextcloudTalkApplication.Companion.getSharedApplication().getResources().getString(R.string.nc_guest);
|
||||
|
||||
if (!TextUtils.isEmpty(participant.getDisplayName())) {
|
||||
displayName = participant.getDisplayName();
|
||||
}
|
||||
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.simpleDraweeView.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(ApiUtils.getUrlForAvatarWithNameForGuests(userEntity.getBaseUrl(),
|
||||
displayName, R.dimen.avatar_size), null))
|
||||
.build();
|
||||
holder.simpleDraweeView.setController(draweeController);
|
||||
|
||||
} else {
|
||||
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setOldController(holder.simpleDraweeView.getController())
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(ApiUtils.getUrlForAvatarWithName(userEntity.getBaseUrl(),
|
||||
participant.getUserId(), R.dimen.avatar_size), null))
|
||||
.build();
|
||||
holder.simpleDraweeView.setController(draweeController);
|
||||
|
||||
}
|
||||
} else if ("groups".equals(participant.getSource())) {
|
||||
holder.simpleDraweeView.getHierarchy().setImage(new BitmapDrawable(DisplayUtils.getRoundedBitmapFromVectorDrawableResource(activityContext.getResources(), R.drawable.ic_people_group_white_24px)), 100, true);
|
||||
}
|
||||
|
||||
Resources resources = activityContext.getResources();
|
||||
|
||||
if (header == null) {
|
||||
Participant.ParticipantFlags participantFlags = participant.getParticipantFlags();
|
||||
switch (participantFlags) {
|
||||
case NOT_IN_CALL:
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.GONE);
|
||||
holder.videoCallImageView.setVisibility(View.GONE);
|
||||
break;
|
||||
case IN_CALL:
|
||||
holder.voiceOrSimpleCallImageView.setBackground(resources.getDrawable(R.drawable.shape_call_bubble));
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.VISIBLE);
|
||||
holder.videoCallImageView.setVisibility(View.GONE);
|
||||
break;
|
||||
case IN_CALL_WITH_AUDIO:
|
||||
holder.voiceOrSimpleCallImageView.setBackground(resources.getDrawable(R.drawable.shape_voice_bubble));
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.VISIBLE);
|
||||
holder.videoCallImageView.setVisibility(View.GONE);
|
||||
break;
|
||||
case IN_CALL_WITH_VIDEO:
|
||||
holder.voiceOrSimpleCallImageView.setBackground(resources.getDrawable(R.drawable.shape_call_bubble));
|
||||
holder.videoCallImageView.setBackground(resources.getDrawable(R.drawable.shape_video_bubble));
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.VISIBLE);
|
||||
holder.videoCallImageView.setVisibility(View.VISIBLE);
|
||||
break;
|
||||
case IN_CALL_WITH_AUDIO_AND_VIDEO:
|
||||
holder.voiceOrSimpleCallImageView.setBackground(resources.getDrawable(R.drawable.shape_voice_bubble));
|
||||
holder.videoCallImageView.setBackground(resources.getDrawable(R.drawable.shape_video_bubble));
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.VISIBLE);
|
||||
holder.videoCallImageView.setVisibility(View.VISIBLE);
|
||||
break;
|
||||
default:
|
||||
holder.voiceOrSimpleCallImageView.setVisibility(View.GONE);
|
||||
holder.videoCallImageView.setVisibility(View.GONE);
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
if (holder.contactMentionId != null) {
|
||||
String userType = "";
|
||||
|
||||
switch (new EnumParticipantTypeConverter().convertToInt(participant.getType())) {
|
||||
case 1:
|
||||
//userType = NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_owner);
|
||||
//break;
|
||||
case 2:
|
||||
userType = NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_moderator);
|
||||
break;
|
||||
case 3:
|
||||
userType = NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_user);
|
||||
break;
|
||||
case 4:
|
||||
userType = NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_guest);
|
||||
break;
|
||||
case 5:
|
||||
userType = NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_following_link);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
if (!holder.contactMentionId.getText().equals(userType)) {
|
||||
holder.contactMentionId.setText(userType);
|
||||
holder.contactMentionId.setTextColor(activityContext.getResources().getColor(R.color.colorPrimary));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return participant.getDisplayName() != null &&
|
||||
(Pattern.compile(constraint, Pattern.CASE_INSENSITIVE | Pattern.LITERAL).matcher(participant.getDisplayName().trim()).find() ||
|
||||
Pattern.compile(constraint, Pattern.CASE_INSENSITIVE | Pattern.LITERAL).matcher(participant.getUserId().trim()).find());
|
||||
}
|
||||
|
||||
@Override
|
||||
public GenericTextHeaderItem getHeader() {
|
||||
return header;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setHeader(GenericTextHeaderItem header) {
|
||||
this.header = header;
|
||||
}
|
||||
|
||||
|
||||
static class UserItemViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.name_text)
|
||||
public EmojiTextView contactDisplayName;
|
||||
@BindView(R.id.simple_drawee_view)
|
||||
public SimpleDraweeView simpleDraweeView;
|
||||
@Nullable
|
||||
@BindView(R.id.secondary_text)
|
||||
public EmojiTextView contactMentionId;
|
||||
@Nullable
|
||||
@BindView(R.id.voiceOrSimpleCallImageView)
|
||||
ImageView voiceOrSimpleCallImageView;
|
||||
@Nullable
|
||||
@BindView(R.id.videoCallImageView)
|
||||
ImageView videoCallImageView;
|
||||
@Nullable
|
||||
@BindView(R.id.checkedImageView)
|
||||
ImageView checkedImageView;
|
||||
|
||||
/**
|
||||
* Default constructor.
|
||||
*/
|
||||
UserItemViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -54,150 +54,154 @@ import javax.inject.Inject;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class MagicIncomingTextMessageViewHolder
|
||||
extends MessageHolders.IncomingTextMessageViewHolder<ChatMessage> {
|
||||
extends MessageHolders.IncomingTextMessageViewHolder<ChatMessage> {
|
||||
|
||||
@BindView(R.id.messageAuthor)
|
||||
EmojiTextView messageAuthor;
|
||||
@BindView(R.id.messageAuthor)
|
||||
EmojiTextView messageAuthor;
|
||||
|
||||
@BindView(R.id.messageText)
|
||||
EmojiTextView messageText;
|
||||
@BindView(R.id.messageText)
|
||||
EmojiTextView messageText;
|
||||
|
||||
@BindView(R.id.messageUserAvatar)
|
||||
SimpleDraweeView messageUserAvatarView;
|
||||
@BindView(R.id.messageUserAvatar)
|
||||
SimpleDraweeView messageUserAvatarView;
|
||||
|
||||
@BindView(R.id.messageTime)
|
||||
TextView messageTimeView;
|
||||
@BindView(R.id.messageTime)
|
||||
TextView messageTimeView;
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
@Inject
|
||||
Context context;
|
||||
@Inject
|
||||
Context context;
|
||||
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
|
||||
private View itemView;
|
||||
private View itemView;
|
||||
|
||||
public MagicIncomingTextMessageViewHolder(View itemView) {
|
||||
super(itemView);
|
||||
ButterKnife.bind(this, itemView);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
public MagicIncomingTextMessageViewHolder(View itemView) {
|
||||
super(itemView);
|
||||
ButterKnife.bind(this, itemView);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
this.itemView = itemView;
|
||||
this.itemView = itemView;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onBind(ChatMessage message) {
|
||||
super.onBind(message);
|
||||
String author;
|
||||
|
||||
if (!TextUtils.isEmpty(author = message.getActorDisplayName())) {
|
||||
messageAuthor.setText(author);
|
||||
} else {
|
||||
messageAuthor.setText(R.string.nc_nick_guest);
|
||||
}
|
||||
|
||||
if (!message.isGrouped() && !message.isOneToOneConversation()) {
|
||||
messageUserAvatarView.setVisibility(View.VISIBLE);
|
||||
if (message.getActorType().equals("guests")) {
|
||||
// do nothing, avatar is set
|
||||
} else if (message.getActorType().equals("bots") && message.getActorId()
|
||||
.equals("changelog")) {
|
||||
messageUserAvatarView.setController(null);
|
||||
Drawable[] layers = new Drawable[2];
|
||||
layers[0] = context.getDrawable(R.drawable.ic_launcher_background);
|
||||
layers[1] = context.getDrawable(R.drawable.ic_launcher_foreground);
|
||||
LayerDrawable layerDrawable = new LayerDrawable(layers);
|
||||
|
||||
@Override
|
||||
public void onBind(ChatMessage message) {
|
||||
super.onBind(message);
|
||||
String author;
|
||||
messageUserAvatarView.getHierarchy()
|
||||
.setPlaceholderImage(DisplayUtils.getRoundedDrawable(layerDrawable));
|
||||
} else if (message.getActorType().equals("bots")) {
|
||||
messageUserAvatarView.setController(null);
|
||||
TextDrawable drawable =
|
||||
TextDrawable.builder().beginConfig().bold().endConfig().buildRound(">",
|
||||
context.getResources().getColor(R.color.black));
|
||||
messageUserAvatarView.setVisibility(View.VISIBLE);
|
||||
messageUserAvatarView.getHierarchy().setPlaceholderImage(drawable);
|
||||
}
|
||||
} else {
|
||||
if (message.isOneToOneConversation()) {
|
||||
messageUserAvatarView.setVisibility(View.GONE);
|
||||
} else {
|
||||
messageUserAvatarView.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
messageAuthor.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(author = message.getActorDisplayName())) {
|
||||
messageAuthor.setText(author);
|
||||
} else {
|
||||
messageAuthor.setText(R.string.nc_nick_guest);
|
||||
}
|
||||
Resources resources = itemView.getResources();
|
||||
|
||||
if (!message.isGrouped() && !message.isOneToOneConversation()) {
|
||||
messageUserAvatarView.setVisibility(View.VISIBLE);
|
||||
if (message.getActorType().equals("guests")) {
|
||||
// do nothing, avatar is set
|
||||
} else if (message.getActorType().equals("bots") && message.getActorId().equals("changelog")) {
|
||||
messageUserAvatarView.setController(null);
|
||||
Drawable[] layers = new Drawable[2];
|
||||
layers[0] = context.getDrawable(R.drawable.ic_launcher_background);
|
||||
layers[1] = context.getDrawable(R.drawable.ic_launcher_foreground);
|
||||
LayerDrawable layerDrawable = new LayerDrawable(layers);
|
||||
int bg_bubble_color = resources.getColor(R.color.bg_message_list_incoming_bubble);
|
||||
|
||||
messageUserAvatarView.getHierarchy().setPlaceholderImage(DisplayUtils.getRoundedDrawable(layerDrawable));
|
||||
} else if (message.getActorType().equals("bots")) {
|
||||
messageUserAvatarView.setController(null);
|
||||
TextDrawable drawable = TextDrawable.builder().beginConfig().bold().endConfig().buildRound(">",
|
||||
context.getResources().getColor(R.color.black));
|
||||
messageUserAvatarView.setVisibility(View.VISIBLE);
|
||||
messageUserAvatarView.getHierarchy().setPlaceholderImage(drawable);
|
||||
}
|
||||
} else {
|
||||
if (message.isOneToOneConversation()) {
|
||||
messageUserAvatarView.setVisibility(View.GONE);
|
||||
int bubbleResource = R.drawable.shape_incoming_message;
|
||||
|
||||
if (message.isGrouped) {
|
||||
bubbleResource = R.drawable.shape_grouped_incoming_message;
|
||||
}
|
||||
|
||||
Drawable bubbleDrawable = DisplayUtils.getMessageSelector(bg_bubble_color,
|
||||
resources.getColor(R.color.transparent),
|
||||
bg_bubble_color, bubbleResource);
|
||||
ViewCompat.setBackground(bubble, bubbleDrawable);
|
||||
|
||||
HashMap<String, HashMap<String, String>> messageParameters = message.getMessageParameters();
|
||||
|
||||
itemView.setSelected(false);
|
||||
messageTimeView.setTextColor(context.getResources().getColor(R.color.warm_grey_four));
|
||||
|
||||
FlexboxLayout.LayoutParams layoutParams =
|
||||
(FlexboxLayout.LayoutParams) messageTimeView.getLayoutParams();
|
||||
layoutParams.setWrapBefore(false);
|
||||
|
||||
Spannable messageString = new SpannableString(message.getText());
|
||||
|
||||
float textSize = context.getResources().getDimension(R.dimen.chat_text_size);
|
||||
|
||||
if (messageParameters != null && messageParameters.size() > 0) {
|
||||
for (String key : messageParameters.keySet()) {
|
||||
Map<String, String> individualHashMap = message.getMessageParameters().get(key);
|
||||
if (individualHashMap != null) {
|
||||
if (individualHashMap.get("type").equals("user") || individualHashMap.get("type")
|
||||
.equals("guest") || individualHashMap.get("type").equals("call")) {
|
||||
if (individualHashMap.get("id").equals(message.getActiveUser().getUserId())) {
|
||||
messageString =
|
||||
DisplayUtils.searchAndReplaceWithMentionSpan(messageText.getContext(),
|
||||
messageString,
|
||||
individualHashMap.get("id"),
|
||||
individualHashMap.get("name"),
|
||||
individualHashMap.get("type"),
|
||||
userUtils.getUserById(message.getActiveUser().getUserId()),
|
||||
R.xml.chip_you);
|
||||
} else {
|
||||
messageUserAvatarView.setVisibility(View.INVISIBLE);
|
||||
messageString =
|
||||
DisplayUtils.searchAndReplaceWithMentionSpan(messageText.getContext(),
|
||||
messageString,
|
||||
individualHashMap.get("id"),
|
||||
individualHashMap.get("name"),
|
||||
individualHashMap.get("type"),
|
||||
userUtils.getUserById(message.getActiveUser().getUserId()),
|
||||
R.xml.chip_others);
|
||||
}
|
||||
messageAuthor.setVisibility(View.GONE);
|
||||
} else if (individualHashMap.get("type").equals("file")) {
|
||||
itemView.setOnClickListener(v -> {
|
||||
Intent browserIntent =
|
||||
new Intent(Intent.ACTION_VIEW, Uri.parse(individualHashMap.get("link")));
|
||||
context.startActivity(browserIntent);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
Resources resources = itemView.getResources();
|
||||
|
||||
int bg_bubble_color = resources.getColor(R.color.bg_message_list_incoming_bubble);
|
||||
|
||||
int bubbleResource = R.drawable.shape_incoming_message;
|
||||
|
||||
if (message.isGrouped) {
|
||||
bubbleResource = R.drawable.shape_grouped_incoming_message;
|
||||
}
|
||||
|
||||
Drawable bubbleDrawable = DisplayUtils.getMessageSelector(bg_bubble_color,
|
||||
resources.getColor(R.color.transparent),
|
||||
bg_bubble_color, bubbleResource);
|
||||
ViewCompat.setBackground(bubble, bubbleDrawable);
|
||||
|
||||
HashMap<String, HashMap<String, String>> messageParameters = message.getMessageParameters();
|
||||
|
||||
itemView.setSelected(false);
|
||||
messageTimeView.setTextColor(context.getResources().getColor(R.color.warm_grey_four));
|
||||
|
||||
FlexboxLayout.LayoutParams layoutParams = (FlexboxLayout.LayoutParams) messageTimeView.getLayoutParams();
|
||||
layoutParams.setWrapBefore(false);
|
||||
|
||||
Spannable messageString = new SpannableString(message.getText());
|
||||
|
||||
float textSize = context.getResources().getDimension(R.dimen.chat_text_size);
|
||||
|
||||
if (messageParameters != null && messageParameters.size() > 0) {
|
||||
for (String key : messageParameters.keySet()) {
|
||||
Map<String, String> individualHashMap = message.getMessageParameters().get(key);
|
||||
if (individualHashMap != null) {
|
||||
if (individualHashMap.get("type").equals("user") || individualHashMap.get("type").equals("guest") || individualHashMap.get("type").equals("call")) {
|
||||
if (individualHashMap.get("id").equals(message.getActiveUser().getUserId())) {
|
||||
messageString =
|
||||
DisplayUtils.searchAndReplaceWithMentionSpan(messageText.getContext(),
|
||||
messageString,
|
||||
individualHashMap.get("id"),
|
||||
individualHashMap.get("name"),
|
||||
individualHashMap.get("type"),
|
||||
userUtils.getUserById(message.getActiveUser().getUserId()),
|
||||
R.xml.chip_you);
|
||||
} else {
|
||||
messageString =
|
||||
DisplayUtils.searchAndReplaceWithMentionSpan(messageText.getContext(),
|
||||
messageString,
|
||||
individualHashMap.get("id"),
|
||||
individualHashMap.get("name"),
|
||||
individualHashMap.get("type"),
|
||||
userUtils.getUserById(message.getActiveUser().getUserId()),
|
||||
R.xml.chip_others);
|
||||
}
|
||||
|
||||
} else if (individualHashMap.get("type").equals("file")) {
|
||||
itemView.setOnClickListener(v -> {
|
||||
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(individualHashMap.get("link")));
|
||||
context.startActivity(browserIntent);
|
||||
});
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
} else if (TextMatchers.isMessageWithSingleEmoticonOnly(message.getText())) {
|
||||
textSize = (float) (textSize * 2.5);
|
||||
layoutParams.setWrapBefore(true);
|
||||
itemView.setSelected(true);
|
||||
messageAuthor.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
messageText.setTextSize(TypedValue.COMPLEX_UNIT_PX, textSize);
|
||||
messageTimeView.setLayoutParams(layoutParams);
|
||||
messageText.setText(messageString);
|
||||
}
|
||||
} else if (TextMatchers.isMessageWithSingleEmoticonOnly(message.getText())) {
|
||||
textSize = (float) (textSize * 2.5);
|
||||
layoutParams.setWrapBefore(true);
|
||||
itemView.setSelected(true);
|
||||
messageAuthor.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
messageText.setTextSize(TypedValue.COMPLEX_UNIT_PX, textSize);
|
||||
messageTimeView.setLayoutParams(layoutParams);
|
||||
messageText.setText(messageString);
|
||||
}
|
||||
}
|
@ -48,91 +48,99 @@ import java.util.Map;
|
||||
import javax.inject.Inject;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class MagicOutcomingTextMessageViewHolder extends MessageHolders.OutcomingTextMessageViewHolder<ChatMessage> {
|
||||
@BindView(R.id.messageText)
|
||||
EmojiTextView messageText;
|
||||
public class MagicOutcomingTextMessageViewHolder
|
||||
extends MessageHolders.OutcomingTextMessageViewHolder<ChatMessage> {
|
||||
@BindView(R.id.messageText)
|
||||
EmojiTextView messageText;
|
||||
|
||||
@BindView(R.id.messageTime)
|
||||
TextView messageTimeView;
|
||||
@BindView(R.id.messageTime)
|
||||
TextView messageTimeView;
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
@Inject
|
||||
Context context;
|
||||
@Inject
|
||||
Context context;
|
||||
|
||||
private View itemView;
|
||||
private View itemView;
|
||||
|
||||
public MagicOutcomingTextMessageViewHolder(View itemView) {
|
||||
super(itemView);
|
||||
ButterKnife.bind(this, itemView);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
public MagicOutcomingTextMessageViewHolder(View itemView) {
|
||||
super(itemView);
|
||||
ButterKnife.bind(this, itemView);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
this.itemView = itemView;
|
||||
this.itemView = itemView;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onBind(ChatMessage message) {
|
||||
super.onBind(message);
|
||||
|
||||
HashMap<String, HashMap<String, String>> messageParameters = message.getMessageParameters();
|
||||
|
||||
Spannable messageString = new SpannableString(message.getText());
|
||||
|
||||
itemView.setSelected(false);
|
||||
messageTimeView.setTextColor(context.getResources().getColor(R.color.white60));
|
||||
|
||||
FlexboxLayout.LayoutParams layoutParams =
|
||||
(FlexboxLayout.LayoutParams) messageTimeView.getLayoutParams();
|
||||
layoutParams.setWrapBefore(false);
|
||||
|
||||
float textSize = context.getResources().getDimension(R.dimen.chat_text_size);
|
||||
|
||||
if (messageParameters != null && messageParameters.size() > 0) {
|
||||
for (String key : messageParameters.keySet()) {
|
||||
Map<String, String> individualHashMap = message.getMessageParameters().get(key);
|
||||
if (individualHashMap != null) {
|
||||
if (individualHashMap.get("type").equals("user") || individualHashMap.get("type")
|
||||
.equals("guest") || individualHashMap.get("type").equals("call")) {
|
||||
messageString =
|
||||
DisplayUtils.searchAndReplaceWithMentionSpan(messageText.getContext(),
|
||||
messageString,
|
||||
individualHashMap.get("id"),
|
||||
individualHashMap.get("name"),
|
||||
individualHashMap.get("type"),
|
||||
userUtils.getUserById(message.getActiveUser().getUserId()),
|
||||
R.xml.chip_others);
|
||||
} else if (individualHashMap.get("type").equals("file")) {
|
||||
itemView.setOnClickListener(v -> {
|
||||
Intent browserIntent =
|
||||
new Intent(Intent.ACTION_VIEW, Uri.parse(individualHashMap.get("link")));
|
||||
context.startActivity(browserIntent);
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
} else if (TextMatchers.isMessageWithSingleEmoticonOnly(message.getText())) {
|
||||
textSize = (float) (textSize * 2.5);
|
||||
layoutParams.setWrapBefore(true);
|
||||
messageTimeView.setTextColor(context.getResources().getColor(R.color.warm_grey_four));
|
||||
itemView.setSelected(true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onBind(ChatMessage message) {
|
||||
super.onBind(message);
|
||||
|
||||
HashMap<String, HashMap<String, String>> messageParameters = message.getMessageParameters();
|
||||
|
||||
Spannable messageString = new SpannableString(message.getText());
|
||||
|
||||
itemView.setSelected(false);
|
||||
messageTimeView.setTextColor(context.getResources().getColor(R.color.white60));
|
||||
|
||||
FlexboxLayout.LayoutParams layoutParams = (FlexboxLayout.LayoutParams) messageTimeView.getLayoutParams();
|
||||
layoutParams.setWrapBefore(false);
|
||||
|
||||
float textSize = context.getResources().getDimension(R.dimen.chat_text_size);
|
||||
|
||||
if (messageParameters != null && messageParameters.size() > 0) {
|
||||
for (String key : messageParameters.keySet()) {
|
||||
Map<String, String> individualHashMap = message.getMessageParameters().get(key);
|
||||
if (individualHashMap != null) {
|
||||
if (individualHashMap.get("type").equals("user") || individualHashMap.get("type").equals("guest") || individualHashMap.get("type").equals("call")) {
|
||||
messageString =
|
||||
DisplayUtils.searchAndReplaceWithMentionSpan(messageText.getContext(),
|
||||
messageString,
|
||||
individualHashMap.get("id"),
|
||||
individualHashMap.get("name"),
|
||||
individualHashMap.get("type"),
|
||||
userUtils.getUserById(message.getActiveUser().getUserId()),
|
||||
R.xml.chip_others);
|
||||
} else if (individualHashMap.get("type").equals("file")) {
|
||||
itemView.setOnClickListener(v -> {
|
||||
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(individualHashMap.get("link")));
|
||||
context.startActivity(browserIntent);
|
||||
});
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
} else if (TextMatchers.isMessageWithSingleEmoticonOnly(message.getText())) {
|
||||
textSize = (float) (textSize * 2.5);
|
||||
layoutParams.setWrapBefore(true);
|
||||
messageTimeView.setTextColor(context.getResources().getColor(R.color.warm_grey_four));
|
||||
itemView.setSelected(true);
|
||||
}
|
||||
|
||||
Resources resources = NextcloudTalkApplication.Companion.getSharedApplication().getResources();
|
||||
if (message.isGrouped) {
|
||||
Drawable bubbleDrawable =
|
||||
DisplayUtils.getMessageSelector(resources.getColor(R.color.bg_message_list_outcoming_bubble),
|
||||
resources.getColor(R.color.transparent),
|
||||
resources.getColor(R.color.bg_message_list_outcoming_bubble), R.drawable.shape_grouped_outcoming_message);
|
||||
ViewCompat.setBackground(bubble, bubbleDrawable);
|
||||
} else {
|
||||
Drawable bubbleDrawable = DisplayUtils.getMessageSelector(resources.getColor(R.color.bg_message_list_outcoming_bubble),
|
||||
resources.getColor(R.color.transparent),
|
||||
resources.getColor(R.color.bg_message_list_outcoming_bubble), R.drawable.shape_outcoming_message);
|
||||
ViewCompat.setBackground(bubble, bubbleDrawable);
|
||||
}
|
||||
|
||||
messageText.setTextSize(TypedValue.COMPLEX_UNIT_PX, textSize);
|
||||
messageTimeView.setLayoutParams(layoutParams);
|
||||
messageText.setText(messageString);
|
||||
Resources resources = NextcloudTalkApplication.Companion.getSharedApplication().getResources();
|
||||
if (message.isGrouped) {
|
||||
Drawable bubbleDrawable =
|
||||
DisplayUtils.getMessageSelector(
|
||||
resources.getColor(R.color.bg_message_list_outcoming_bubble),
|
||||
resources.getColor(R.color.transparent),
|
||||
resources.getColor(R.color.bg_message_list_outcoming_bubble),
|
||||
R.drawable.shape_grouped_outcoming_message);
|
||||
ViewCompat.setBackground(bubble, bubbleDrawable);
|
||||
} else {
|
||||
Drawable bubbleDrawable = DisplayUtils.getMessageSelector(
|
||||
resources.getColor(R.color.bg_message_list_outcoming_bubble),
|
||||
resources.getColor(R.color.transparent),
|
||||
resources.getColor(R.color.bg_message_list_outcoming_bubble),
|
||||
R.drawable.shape_outcoming_message);
|
||||
ViewCompat.setBackground(bubble, bubbleDrawable);
|
||||
}
|
||||
|
||||
messageText.setTextSize(TypedValue.COMPLEX_UNIT_PX, textSize);
|
||||
messageTimeView.setLayoutParams(layoutParams);
|
||||
messageText.setText(messageString);
|
||||
}
|
||||
}
|
||||
|
@ -55,126 +55,144 @@ import javax.inject.Inject;
|
||||
import okhttp3.OkHttpClient;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class MagicPreviewMessageViewHolder extends MessageHolders.IncomingImageMessageViewHolder<ChatMessage> {
|
||||
public class MagicPreviewMessageViewHolder
|
||||
extends MessageHolders.IncomingImageMessageViewHolder<ChatMessage> {
|
||||
|
||||
@BindView(R.id.messageText)
|
||||
EmojiTextView messageText;
|
||||
@BindView(R.id.messageText)
|
||||
EmojiTextView messageText;
|
||||
|
||||
@Inject
|
||||
Context context;
|
||||
@Inject
|
||||
Context context;
|
||||
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
|
||||
public MagicPreviewMessageViewHolder(View itemView) {
|
||||
super(itemView);
|
||||
ButterKnife.bind(this, itemView);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
}
|
||||
public MagicPreviewMessageViewHolder(View itemView) {
|
||||
super(itemView);
|
||||
ButterKnife.bind(this, itemView);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
}
|
||||
|
||||
@SuppressLint("SetTextI18n")
|
||||
@Override
|
||||
public void onBind(ChatMessage message) {
|
||||
super.onBind(message);
|
||||
if (userAvatar != null) {
|
||||
if (message.isGrouped || message.isOneToOneConversation) {
|
||||
if (message.isOneToOneConversation) {
|
||||
userAvatar.setVisibility(View.GONE);
|
||||
} else {
|
||||
userAvatar.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
} else {
|
||||
userAvatar.setVisibility(View.VISIBLE);
|
||||
|
||||
if ("bots".equals(message.getActorType()) && "changelog".equals(message.getActorId())) {
|
||||
Drawable[] layers = new Drawable[2];
|
||||
layers[0] = context.getDrawable(R.drawable.ic_launcher_background);
|
||||
layers[1] = context.getDrawable(R.drawable.ic_launcher_foreground);
|
||||
LayerDrawable layerDrawable = new LayerDrawable(layers);
|
||||
|
||||
userAvatar.getHierarchy().setPlaceholderImage(DisplayUtils.getRoundedDrawable(layerDrawable));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (message.getMessageType() == ChatMessage.MessageType.SINGLE_NC_ATTACHMENT_MESSAGE) {
|
||||
// it's a preview for a Nextcloud share
|
||||
messageText.setText(message.getSelectedIndividualHashMap().get("name"));
|
||||
DisplayUtils.setClickableString(message.getSelectedIndividualHashMap().get("name"), message.getSelectedIndividualHashMap().get("link"), messageText);
|
||||
if (message.getSelectedIndividualHashMap().containsKey("mimetype")) {
|
||||
image.getHierarchy().setPlaceholderImage(context.getDrawable(DrawableUtils.INSTANCE.getDrawableResourceIdForMimeType(message.getSelectedIndividualHashMap().get("mimetype"))));
|
||||
} else {
|
||||
fetchFileInformation("/" + message.getSelectedIndividualHashMap().get("path"), message.getActiveUser());
|
||||
}
|
||||
|
||||
image.setOnClickListener(v -> {
|
||||
|
||||
String accountString =
|
||||
message.getActiveUser().getUsername() + "@" + message.getActiveUser().getBaseUrl().replace("https://", "").replace("http://", "");
|
||||
|
||||
if (AccountUtils.INSTANCE.canWeOpenFilesApp(context, accountString)) {
|
||||
Intent filesAppIntent = new Intent(Intent.ACTION_VIEW, null);
|
||||
final ComponentName componentName = new ComponentName(context.getString(R.string.nc_import_accounts_from), "com.owncloud.android.ui.activity.FileDisplayActivity");
|
||||
filesAppIntent.setComponent(componentName);
|
||||
filesAppIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
filesAppIntent.setPackage(context.getString(R.string.nc_import_accounts_from));
|
||||
filesAppIntent.putExtra(BundleKeys.INSTANCE.getKEY_ACCOUNT(), accountString);
|
||||
filesAppIntent.putExtra(BundleKeys.INSTANCE.getKEY_FILE_ID(), message.getSelectedIndividualHashMap().get("id"));
|
||||
context.startActivity(filesAppIntent);
|
||||
} else {
|
||||
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(message.getSelectedIndividualHashMap().get("link")));
|
||||
browserIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
context.startActivity(browserIntent);
|
||||
}
|
||||
});
|
||||
} else if (message.getMessageType() == ChatMessage.MessageType.SINGLE_LINK_GIPHY_MESSAGE) {
|
||||
messageText.setText("GIPHY");
|
||||
DisplayUtils.setClickableString("GIPHY", "https://giphy.com", messageText);
|
||||
} else if (message.getMessageType() == ChatMessage.MessageType.SINGLE_LINK_TENOR_MESSAGE) {
|
||||
messageText.setText("Tenor");
|
||||
DisplayUtils.setClickableString("Tenor", "https://tenor.com", messageText);
|
||||
@SuppressLint("SetTextI18n")
|
||||
@Override
|
||||
public void onBind(ChatMessage message) {
|
||||
super.onBind(message);
|
||||
if (userAvatar != null) {
|
||||
if (message.isGrouped || message.isOneToOneConversation) {
|
||||
if (message.isOneToOneConversation) {
|
||||
userAvatar.setVisibility(View.GONE);
|
||||
} else {
|
||||
if (message.getMessageType().equals(ChatMessage.MessageType.SINGLE_LINK_IMAGE_MESSAGE)) {
|
||||
image.setOnClickListener(v -> {
|
||||
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(message.getImageUrl()));
|
||||
browserIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
context.startActivity(browserIntent);
|
||||
});
|
||||
} else {
|
||||
image.setOnClickListener(null);
|
||||
}
|
||||
messageText.setText("");
|
||||
userAvatar.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
} else {
|
||||
userAvatar.setVisibility(View.VISIBLE);
|
||||
|
||||
if ("bots".equals(message.getActorType()) && "changelog".equals(message.getActorId())) {
|
||||
Drawable[] layers = new Drawable[2];
|
||||
layers[0] = context.getDrawable(R.drawable.ic_launcher_background);
|
||||
layers[1] = context.getDrawable(R.drawable.ic_launcher_foreground);
|
||||
LayerDrawable layerDrawable = new LayerDrawable(layers);
|
||||
|
||||
userAvatar.getHierarchy()
|
||||
.setPlaceholderImage(DisplayUtils.getRoundedDrawable(layerDrawable));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void fetchFileInformation(String url, UserEntity activeUser) {
|
||||
Single.fromCallable(new Callable<ReadFilesystemOperation>() {
|
||||
@Override
|
||||
public ReadFilesystemOperation call() {
|
||||
return new ReadFilesystemOperation(okHttpClient, activeUser, url, 0);
|
||||
if (message.getMessageType() == ChatMessage.MessageType.SINGLE_NC_ATTACHMENT_MESSAGE) {
|
||||
// it's a preview for a Nextcloud share
|
||||
messageText.setText(message.getSelectedIndividualHashMap().get("name"));
|
||||
DisplayUtils.setClickableString(message.getSelectedIndividualHashMap().get("name"),
|
||||
message.getSelectedIndividualHashMap().get("link"), messageText);
|
||||
if (message.getSelectedIndividualHashMap().containsKey("mimetype")) {
|
||||
image.getHierarchy()
|
||||
.setPlaceholderImage(context.getDrawable(
|
||||
DrawableUtils.INSTANCE.getDrawableResourceIdForMimeType(
|
||||
message.getSelectedIndividualHashMap().get("mimetype"))));
|
||||
} else {
|
||||
fetchFileInformation("/" + message.getSelectedIndividualHashMap().get("path"),
|
||||
message.getActiveUser());
|
||||
}
|
||||
|
||||
image.setOnClickListener(v -> {
|
||||
|
||||
String accountString =
|
||||
message.getActiveUser().getUsername() + "@" + message.getActiveUser()
|
||||
.getBaseUrl()
|
||||
.replace("https://", "")
|
||||
.replace("http://", "");
|
||||
|
||||
if (AccountUtils.INSTANCE.canWeOpenFilesApp(context, accountString)) {
|
||||
Intent filesAppIntent = new Intent(Intent.ACTION_VIEW, null);
|
||||
final ComponentName componentName =
|
||||
new ComponentName(context.getString(R.string.nc_import_accounts_from),
|
||||
"com.owncloud.android.ui.activity.FileDisplayActivity");
|
||||
filesAppIntent.setComponent(componentName);
|
||||
filesAppIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
filesAppIntent.setPackage(context.getString(R.string.nc_import_accounts_from));
|
||||
filesAppIntent.putExtra(BundleKeys.INSTANCE.getKEY_ACCOUNT(), accountString);
|
||||
filesAppIntent.putExtra(BundleKeys.INSTANCE.getKEY_FILE_ID(),
|
||||
message.getSelectedIndividualHashMap().get("id"));
|
||||
context.startActivity(filesAppIntent);
|
||||
} else {
|
||||
Intent browserIntent = new Intent(Intent.ACTION_VIEW,
|
||||
Uri.parse(message.getSelectedIndividualHashMap().get("link")));
|
||||
browserIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
context.startActivity(browserIntent);
|
||||
}
|
||||
});
|
||||
} else if (message.getMessageType() == ChatMessage.MessageType.SINGLE_LINK_GIPHY_MESSAGE) {
|
||||
messageText.setText("GIPHY");
|
||||
DisplayUtils.setClickableString("GIPHY", "https://giphy.com", messageText);
|
||||
} else if (message.getMessageType() == ChatMessage.MessageType.SINGLE_LINK_TENOR_MESSAGE) {
|
||||
messageText.setText("Tenor");
|
||||
DisplayUtils.setClickableString("Tenor", "https://tenor.com", messageText);
|
||||
} else {
|
||||
if (message.getMessageType().equals(ChatMessage.MessageType.SINGLE_LINK_IMAGE_MESSAGE)) {
|
||||
image.setOnClickListener(v -> {
|
||||
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(message.getImageUrl()));
|
||||
browserIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
context.startActivity(browserIntent);
|
||||
});
|
||||
} else {
|
||||
image.setOnClickListener(null);
|
||||
}
|
||||
messageText.setText("");
|
||||
}
|
||||
}
|
||||
|
||||
private void fetchFileInformation(String url, UserEntity activeUser) {
|
||||
Single.fromCallable(new Callable<ReadFilesystemOperation>() {
|
||||
@Override
|
||||
public ReadFilesystemOperation call() {
|
||||
return new ReadFilesystemOperation(okHttpClient, activeUser, url, 0);
|
||||
}
|
||||
}).observeOn(Schedulers.io())
|
||||
.subscribe(new SingleObserver<ReadFilesystemOperation>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onSuccess(ReadFilesystemOperation readFilesystemOperation) {
|
||||
DavResponse davResponse = readFilesystemOperation.readRemotePath();
|
||||
if (davResponse.getData() != null) {
|
||||
List<BrowserFile> browserFileList = (List<BrowserFile>) davResponse.getData();
|
||||
if (!browserFileList.isEmpty()) {
|
||||
new Handler(context.getMainLooper()).post(() -> image.getHierarchy()
|
||||
.setPlaceholderImage(context.getDrawable(
|
||||
DrawableUtils.INSTANCE.getDrawableResourceIdForMimeType(
|
||||
browserFileList.get(0).getMimeType()))));
|
||||
}
|
||||
}
|
||||
}).observeOn(Schedulers.io())
|
||||
.subscribe(new SingleObserver<ReadFilesystemOperation>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onSuccess(ReadFilesystemOperation readFilesystemOperation) {
|
||||
DavResponse davResponse = readFilesystemOperation.readRemotePath();
|
||||
if (davResponse.getData() != null) {
|
||||
List<BrowserFile> browserFileList = (List<BrowserFile>) davResponse.getData();
|
||||
if (!browserFileList.isEmpty()) {
|
||||
new Handler(context.getMainLooper()).post(() -> image.getHierarchy().setPlaceholderImage(context.getDrawable(DrawableUtils.INSTANCE.getDrawableResourceIdForMimeType(browserFileList.get(0).getMimeType()))));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
}
|
||||
});
|
||||
|
||||
}
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -38,48 +38,54 @@ import java.util.Map;
|
||||
import javax.inject.Inject;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class MagicSystemMessageViewHolder extends MessageHolders.IncomingTextMessageViewHolder<ChatMessage> {
|
||||
public class MagicSystemMessageViewHolder
|
||||
extends MessageHolders.IncomingTextMessageViewHolder<ChatMessage> {
|
||||
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
|
||||
@Inject
|
||||
Context context;
|
||||
@Inject
|
||||
Context context;
|
||||
|
||||
public MagicSystemMessageViewHolder(View itemView) {
|
||||
super(itemView);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
}
|
||||
public MagicSystemMessageViewHolder(View itemView) {
|
||||
super(itemView);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onBind(ChatMessage message) {
|
||||
super.onBind(message);
|
||||
@Override
|
||||
public void onBind(ChatMessage message) {
|
||||
super.onBind(message);
|
||||
|
||||
Resources resources = itemView.getResources();
|
||||
int normalColor = resources.getColor(R.color.bg_message_list_incoming_bubble);
|
||||
int pressedColor;
|
||||
int mentionColor;
|
||||
Resources resources = itemView.getResources();
|
||||
int normalColor = resources.getColor(R.color.bg_message_list_incoming_bubble);
|
||||
int pressedColor;
|
||||
int mentionColor;
|
||||
|
||||
pressedColor = normalColor;
|
||||
mentionColor = resources.getColor(R.color.nc_author_text);
|
||||
|
||||
pressedColor = normalColor;
|
||||
mentionColor = resources.getColor(R.color.nc_author_text);
|
||||
Drawable bubbleDrawable = DisplayUtils.getMessageSelector(normalColor,
|
||||
resources.getColor(R.color.transparent), pressedColor,
|
||||
R.drawable.shape_grouped_incoming_message);
|
||||
ViewCompat.setBackground(bubble, bubbleDrawable);
|
||||
|
||||
Drawable bubbleDrawable = DisplayUtils.getMessageSelector(normalColor,
|
||||
resources.getColor(R.color.transparent), pressedColor,
|
||||
R.drawable.shape_grouped_incoming_message);
|
||||
ViewCompat.setBackground(bubble, bubbleDrawable);
|
||||
Spannable messageString = new SpannableString(message.getText());
|
||||
|
||||
Spannable messageString = new SpannableString(message.getText());
|
||||
|
||||
if (message.getMessageParameters() != null && message.getMessageParameters().size() > 0) {
|
||||
for (String key : message.getMessageParameters().keySet()) {
|
||||
Map<String, String> individualHashMap = message.getMessageParameters().get(key);
|
||||
if (individualHashMap != null && (individualHashMap.get("type").equals("user") || individualHashMap.get("type").equals("guest") || individualHashMap.get("type").equals("call"))) {
|
||||
messageString = DisplayUtils.searchAndColor(messageString, "@" + individualHashMap.get("name"), mentionColor);
|
||||
}
|
||||
}
|
||||
if (message.getMessageParameters() != null && message.getMessageParameters().size() > 0) {
|
||||
for (String key : message.getMessageParameters().keySet()) {
|
||||
Map<String, String> individualHashMap = message.getMessageParameters().get(key);
|
||||
if (individualHashMap != null && (individualHashMap.get("type").equals("user")
|
||||
|| individualHashMap.get("type").equals("guest")
|
||||
|| individualHashMap.get("type").equals("call"))) {
|
||||
messageString =
|
||||
DisplayUtils.searchAndColor(messageString, "@" + individualHashMap.get("name"),
|
||||
mentionColor);
|
||||
}
|
||||
|
||||
text.setText(messageString);
|
||||
}
|
||||
}
|
||||
|
||||
text.setText(messageString);
|
||||
}
|
||||
}
|
||||
|
@ -24,27 +24,28 @@ import android.view.View;
|
||||
import com.nextcloud.talk.models.json.chat.ChatMessage;
|
||||
import com.stfalcon.chatkit.messages.MessageHolders;
|
||||
|
||||
public class MagicUnreadNoticeMessageViewHolder extends MessageHolders.SystemMessageViewHolder<ChatMessage> {
|
||||
public class MagicUnreadNoticeMessageViewHolder
|
||||
extends MessageHolders.SystemMessageViewHolder<ChatMessage> {
|
||||
|
||||
public MagicUnreadNoticeMessageViewHolder(View itemView) {
|
||||
super(itemView);
|
||||
}
|
||||
public MagicUnreadNoticeMessageViewHolder(View itemView) {
|
||||
super(itemView);
|
||||
}
|
||||
|
||||
public MagicUnreadNoticeMessageViewHolder(View itemView, Object payload) {
|
||||
super(itemView, payload);
|
||||
}
|
||||
public MagicUnreadNoticeMessageViewHolder(View itemView, Object payload) {
|
||||
super(itemView, payload);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void viewDetached() {
|
||||
messagesListAdapter.deleteById("-1");
|
||||
}
|
||||
@Override
|
||||
public void viewDetached() {
|
||||
messagesListAdapter.deleteById("-1");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void viewAttached() {
|
||||
}
|
||||
@Override
|
||||
public void viewAttached() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void viewRecycled() {
|
||||
@Override
|
||||
public void viewRecycled() {
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -54,36 +54,37 @@ import retrofit2.http.Url;
|
||||
|
||||
public interface NcApi {
|
||||
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
- "format" : "json"
|
||||
- "search" : ""
|
||||
- "perPage" : "200"
|
||||
- "itemType" : "call"
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
- "format" : "json"
|
||||
- "search" : ""
|
||||
- "perPage" : "200"
|
||||
- "itemType" : "call"
|
||||
|
||||
Server URL is: baseUrl + ocsApiVersion + /apps/files_sharing/api/v1/sharees
|
||||
Server URL is: baseUrl + ocsApiVersion + /apps/files_sharing/api/v1/sharees
|
||||
|
||||
or if we're on 14 and up:
|
||||
or if we're on 14 and up:
|
||||
|
||||
baseUrl + ocsApiVersion + "/core/autocomplete/get");
|
||||
baseUrl + ocsApiVersion + "/core/autocomplete/get");
|
||||
|
||||
*/
|
||||
@GET
|
||||
Observable<ResponseBody> getContactsWithSearchParam(@Header("Authorization") String authorization, @Url String url,
|
||||
@Nullable @Query("shareTypes[]") List<String> listOfShareTypes, @QueryMap Map<String, Object> options);
|
||||
*/
|
||||
@GET
|
||||
Observable<ResponseBody> getContactsWithSearchParam(@Header("Authorization") String authorization,
|
||||
@Url String url,
|
||||
@Nullable @Query("shareTypes[]") List<String> listOfShareTypes,
|
||||
@QueryMap Map<String, Object> options);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room
|
||||
*/
|
||||
@GET
|
||||
Observable<RoomsOverall> getRooms(@Header("Authorization") String authorization, @Url String url);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room
|
||||
*/
|
||||
@GET
|
||||
Observable<RoomsOverall> getRooms(@Header("Authorization") String authorization, @Url String url);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room/roomToken
|
||||
*/
|
||||
@GET
|
||||
Observable<RoomOverall> getRoom(@Header("Authorization") String authorization, @Url String url);
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room/roomToken
|
||||
*/
|
||||
@GET
|
||||
Observable<RoomOverall> getRoom(@Header("Authorization") String authorization, @Url String url);
|
||||
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
@ -93,9 +94,9 @@ public interface NcApi {
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room
|
||||
*/
|
||||
|
||||
@POST
|
||||
Observable<RoomOverall> createRoom(@Header("Authorization") String authorization, @Url String url,
|
||||
@QueryMap Map<String, String> options);
|
||||
@POST
|
||||
Observable<RoomOverall> createRoom(@Header("Authorization") String authorization, @Url String url,
|
||||
@QueryMap Map<String, String> options);
|
||||
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
@ -104,109 +105,126 @@ public interface NcApi {
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room/roomToken
|
||||
*/
|
||||
|
||||
@FormUrlEncoded
|
||||
@PUT
|
||||
Observable<GenericOverall> renameRoom(@Header("Authorization") String authorization, @Url String url,
|
||||
@Field("roomName") String roomName);
|
||||
@FormUrlEncoded
|
||||
@PUT
|
||||
Observable<GenericOverall> renameRoom(@Header("Authorization") String authorization,
|
||||
@Url String url,
|
||||
@Field("roomName") String roomName);
|
||||
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
- "newParticipant" : "user"
|
||||
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
- "newParticipant" : "user"
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room/roomToken/participants
|
||||
*/
|
||||
@POST
|
||||
Observable<AddParticipantOverall> addParticipant(@Header("Authorization") String authorization,
|
||||
@Url String url,
|
||||
@QueryMap Map<String, String> options);
|
||||
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room/roomToken/participants
|
||||
*/
|
||||
@POST
|
||||
Observable<AddParticipantOverall> addParticipant(@Header("Authorization") String authorization, @Url String url,
|
||||
@QueryMap Map<String, String> options);
|
||||
// also used for removing a guest from a conversation
|
||||
@DELETE
|
||||
Observable<GenericOverall> removeParticipantFromConversation(
|
||||
@Header("Authorization") String authorization, @Url String url,
|
||||
@Query("participant") String participantId);
|
||||
|
||||
@POST
|
||||
Observable<GenericOverall> promoteUserToModerator(@Header("Authorization") String authorization,
|
||||
@Url String url, @Query("participant") String participantId);
|
||||
|
||||
// also used for removing a guest from a conversation
|
||||
@DELETE
|
||||
Observable<GenericOverall> removeParticipantFromConversation(@Header("Authorization") String authorization, @Url String url, @Query("participant") String participantId);
|
||||
|
||||
@POST
|
||||
Observable<GenericOverall> promoteUserToModerator(@Header("Authorization") String authorization, @Url String url, @Query("participant") String participantId);
|
||||
|
||||
@DELETE
|
||||
Observable<GenericOverall> demoteModeratorToUser(@Header("Authorization") String authorization, @Url String url, @Query("participant") String participantId);
|
||||
@DELETE
|
||||
Observable<GenericOverall> demoteModeratorToUser(@Header("Authorization") String authorization,
|
||||
@Url String url, @Query("participant") String participantId);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room/roomToken/participants/self
|
||||
*/
|
||||
|
||||
@DELETE
|
||||
Observable<GenericOverall> removeSelfFromRoom(@Header("Authorization") String authorization, @Url String url);
|
||||
@DELETE
|
||||
Observable<GenericOverall> removeSelfFromRoom(@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room/roomToken/public
|
||||
*/
|
||||
@POST
|
||||
Observable<GenericOverall> makeRoomPublic(@Header("Authorization") String authorization, @Url String url);
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room/roomToken/public
|
||||
*/
|
||||
@POST
|
||||
Observable<GenericOverall> makeRoomPublic(@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room/roomToken/public
|
||||
*/
|
||||
@DELETE
|
||||
Observable<GenericOverall> makeRoomPrivate(@Header("Authorization") String authorization, @Url String url);
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /room/roomToken/public
|
||||
*/
|
||||
@DELETE
|
||||
Observable<GenericOverall> makeRoomPrivate(@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
@DELETE
|
||||
Observable<GenericOverall> deleteRoom(@Header("Authorization") String authorization, @Url String url);
|
||||
@DELETE
|
||||
Observable<GenericOverall> deleteRoom(@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /call/callToken
|
||||
*/
|
||||
@GET
|
||||
Observable<ParticipantsOverall> getPeersForCall(@Header("Authorization") String authorization, @Url String url);
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /call/callToken
|
||||
*/
|
||||
@GET
|
||||
Observable<ParticipantsOverall> getPeersForCall(@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<RoomOverall> joinRoom(@Nullable @Header("Authorization") String authorization, @Url String url, @Nullable @Field("password") String password);
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<RoomOverall> joinRoom(@Nullable @Header("Authorization") String authorization,
|
||||
@Url String url, @Nullable @Field("password") String password);
|
||||
|
||||
@DELETE
|
||||
Observable<GenericOverall> leaveRoom(@Nullable @Header("Authorization") String authorization, @Url String url);
|
||||
@DELETE
|
||||
Observable<GenericOverall> leaveRoom(@Nullable @Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /call/callToken
|
||||
*/
|
||||
|
||||
@POST
|
||||
Observable<GenericOverall> joinCall(@Nullable @Header("Authorization") String authorization, @Url String url);
|
||||
@POST
|
||||
Observable<GenericOverall> joinCall(@Nullable @Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /call/callToken
|
||||
*/
|
||||
@DELETE
|
||||
Observable<GenericOverall> leaveCall(@Nullable @Header("Authorization") String authorization, @Url String url);
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /call/callToken
|
||||
*/
|
||||
@DELETE
|
||||
Observable<GenericOverall> leaveCall(@Nullable @Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /call/callToken/ping
|
||||
*/
|
||||
@POST
|
||||
Observable<GenericOverall> pingCall(@Nullable @Header("Authorization") String authorization, @Url String url);
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /call/callToken/ping
|
||||
*/
|
||||
@POST
|
||||
Observable<GenericOverall> pingCall(@Nullable @Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
@GET
|
||||
Observable<SignalingSettingsOverall> getSignalingSettings(@Nullable @Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
@GET
|
||||
Observable<SignalingSettingsOverall> getSignalingSettings(
|
||||
@Nullable @Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
- "messages" : "message"
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
- "messages" : "message"
|
||||
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /signaling
|
||||
*/
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<SignalingOverall> sendSignalingMessages(@Nullable @Header("Authorization") String authorization, @Url String url,
|
||||
@Field("messages") String messages);
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /signaling
|
||||
*/
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<SignalingOverall> sendSignalingMessages(
|
||||
@Nullable @Header("Authorization") String authorization, @Url String url,
|
||||
@Field("messages") String messages);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /signaling
|
||||
*/
|
||||
@GET
|
||||
Observable<SignalingOverall> pullSignalingMessages(@Nullable @Header("Authorization") String authorization, @Url
|
||||
String
|
||||
url);
|
||||
/*
|
||||
Server URL is: baseUrl + ocsApiVersion + spreedApiVersion + /signaling
|
||||
*/
|
||||
@GET
|
||||
Observable<SignalingOverall> pullSignalingMessages(
|
||||
@Nullable @Header("Authorization") String authorization, @Url
|
||||
String
|
||||
url);
|
||||
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
@ -215,14 +233,15 @@ public interface NcApi {
|
||||
Server URL is: baseUrl + ocsApiVersion + "/cloud/user"
|
||||
*/
|
||||
|
||||
@GET
|
||||
Observable<UserProfileOverall> getUserProfile(@Header("Authorization") String authorization, @Url String url);
|
||||
@GET
|
||||
Observable<UserProfileOverall> getUserProfile(@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
/*
|
||||
Server URL is: baseUrl + /status.php
|
||||
*/
|
||||
@GET
|
||||
Observable<Status> getServerStatus(@Url String url);
|
||||
/*
|
||||
Server URL is: baseUrl + /status.php
|
||||
*/
|
||||
@GET
|
||||
Observable<Status> getServerStatus(@Url String url);
|
||||
|
||||
|
||||
/*
|
||||
@ -235,52 +254,55 @@ public interface NcApi {
|
||||
Server URL is: baseUrl + ocsApiVersion + "/apps/notifications/api/v2/push
|
||||
*/
|
||||
|
||||
@POST
|
||||
Observable<PushRegistrationOverall> registerDeviceForNotificationsWithNextcloud(@Header("Authorization")
|
||||
String authorization,
|
||||
@Url String url,
|
||||
@QueryMap Map<String,
|
||||
String> options);
|
||||
@POST
|
||||
Observable<PushRegistrationOverall> registerDeviceForNotificationsWithNextcloud(
|
||||
@Header("Authorization")
|
||||
String authorization,
|
||||
@Url String url,
|
||||
@QueryMap Map<String,
|
||||
String> options);
|
||||
|
||||
@DELETE
|
||||
Observable<GenericOverall> unregisterDeviceForNotificationsWithNextcloud(@Header("Authorization")
|
||||
String authorization,
|
||||
@Url String url);
|
||||
@DELETE
|
||||
Observable<GenericOverall> unregisterDeviceForNotificationsWithNextcloud(@Header("Authorization")
|
||||
String authorization,
|
||||
@Url String url);
|
||||
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<Void> registerDeviceForNotificationsWithProxy(@Url String url,
|
||||
@FieldMap Map<String, String> fields);
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<Void> registerDeviceForNotificationsWithProxy(@Url String url,
|
||||
@FieldMap Map<String, String> fields);
|
||||
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
- "deviceIdentifier": "{{deviceIdentifier}}",
|
||||
- "deviceIdentifierSignature": "{{signature}}",
|
||||
- "userPublicKey": "{{userPublicKey}}"
|
||||
*/
|
||||
@DELETE
|
||||
Observable<Void> unregisterDeviceForNotificationsWithProxy(@Url String url,
|
||||
@QueryMap Map<String, String> fields);
|
||||
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
- "deviceIdentifier": "{{deviceIdentifier}}",
|
||||
- "deviceIdentifierSignature": "{{signature}}",
|
||||
- "userPublicKey": "{{userPublicKey}}"
|
||||
*/
|
||||
@DELETE
|
||||
Observable<Void> unregisterDeviceForNotificationsWithProxy(@Url String url,
|
||||
@QueryMap Map<String, String> fields);
|
||||
@FormUrlEncoded
|
||||
@PUT
|
||||
Observable<GenericOverall> setPassword(@Header("Authorization") String authorization,
|
||||
@Url String url,
|
||||
@Field("password") String password);
|
||||
|
||||
@FormUrlEncoded
|
||||
@PUT
|
||||
Observable<GenericOverall> setPassword(@Header("Authorization") String authorization, @Url String url,
|
||||
@Field("password") String password);
|
||||
@GET
|
||||
Observable<CapabilitiesOverall> getCapabilities(@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
@GET
|
||||
Observable<CapabilitiesOverall> getCapabilities(@Header("Authorization") String authorization, @Url String url);
|
||||
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
- "lookIntoFuture": int (0 or 1),
|
||||
- "limit" : int, range 100-200,
|
||||
- "timeout": used with look into future, 30 default, 60 at most
|
||||
- "lastKnownMessageId", int, use one from X-Chat-Last-Given
|
||||
*/
|
||||
@GET
|
||||
Observable<Response<ChatOverall>> pullChatMessages(@Header("Authorization") String authorization, @Url String url,
|
||||
@QueryMap Map<String, Integer> fields);
|
||||
/*
|
||||
QueryMap items are as follows:
|
||||
- "lookIntoFuture": int (0 or 1),
|
||||
- "limit" : int, range 100-200,
|
||||
- "timeout": used with look into future, 30 default, 60 at most
|
||||
- "lastKnownMessageId", int, use one from X-Chat-Last-Given
|
||||
*/
|
||||
@GET
|
||||
Observable<Response<ChatOverall>> pullChatMessages(@Header("Authorization") String authorization,
|
||||
@Url String url,
|
||||
@QueryMap Map<String, Integer> fields);
|
||||
|
||||
/*
|
||||
Fieldmap items are as follows:
|
||||
@ -288,51 +310,56 @@ public interface NcApi {
|
||||
- "actorDisplayName"
|
||||
*/
|
||||
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<GenericOverall> sendChatMessage(@Header("Authorization") String authorization, @Url String url,
|
||||
@Field("message") CharSequence message,
|
||||
@Field("actorDisplayName") String actorDisplayName);
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<GenericOverall> sendChatMessage(@Header("Authorization") String authorization,
|
||||
@Url String url,
|
||||
@Field("message") CharSequence message,
|
||||
@Field("actorDisplayName") String actorDisplayName);
|
||||
|
||||
@GET
|
||||
Observable<MentionOverall> getMentionAutocompleteSuggestions(@Header("Authorization") String authorization,
|
||||
@Url String url, @Query("search") String query,
|
||||
@Nullable @Query("limit") Integer limit);
|
||||
@GET
|
||||
Observable<MentionOverall> getMentionAutocompleteSuggestions(
|
||||
@Header("Authorization") String authorization,
|
||||
@Url String url, @Query("search") String query,
|
||||
@Nullable @Query("limit") Integer limit);
|
||||
|
||||
// Url is: /api/{apiVersion}/room/{token}/pin
|
||||
@POST
|
||||
Observable<GenericOverall> addConversationToFavorites(@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
// Url is: /api/{apiVersion}/room/{token}/pin
|
||||
@POST
|
||||
Observable<GenericOverall> addConversationToFavorites(
|
||||
@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
// Url is: /api/{apiVersion}/room/{token}/favorites
|
||||
@DELETE
|
||||
Observable<GenericOverall> removeConversationFromFavorites(@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
// Url is: /api/{apiVersion}/room/{token}/favorites
|
||||
@DELETE
|
||||
Observable<GenericOverall> removeConversationFromFavorites(
|
||||
@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
@GET
|
||||
Observable<NotificationOverall> getNotification(@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
@GET
|
||||
Observable<NotificationOverall> getNotification(@Header("Authorization") String authorization,
|
||||
@Url String url);
|
||||
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<GenericOverall> setNotificationLevel(@Header("Authorization") String authorization, @Url String url, @Field("level") int level);
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<GenericOverall> setNotificationLevel(@Header("Authorization") String authorization,
|
||||
@Url String url, @Field("level") int level);
|
||||
|
||||
@FormUrlEncoded
|
||||
@PUT
|
||||
Observable<GenericOverall> setReadOnlyState(@Header("Authorization") String authorization, @Url String url, @Field("viewState") int state);
|
||||
@FormUrlEncoded
|
||||
@PUT
|
||||
Observable<GenericOverall> setReadOnlyState(@Header("Authorization") String authorization,
|
||||
@Url String url, @Field("viewState") int state);
|
||||
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<Void> createRemoteShare(@Nullable @Header("Authorization") String authorization,
|
||||
@Url String url,
|
||||
@Field("path") String remotePath,
|
||||
@Field("shareWith") String roomToken,
|
||||
@Field("shareType") String shareType);
|
||||
|
||||
@FormUrlEncoded
|
||||
@POST
|
||||
Observable<Void> createRemoteShare(@Nullable @Header("Authorization") String authorization, @Url String url,
|
||||
@Field("path") String remotePath,
|
||||
@Field("shareWith") String roomToken,
|
||||
@Field("shareType") String shareType);
|
||||
|
||||
@FormUrlEncoded
|
||||
@PUT
|
||||
Observable<GenericOverall> setLobbyForConversation(@Header("Authorization") String authorization,
|
||||
@Url String url, @Field("viewState") Integer state,
|
||||
@Field("timer") Long timer);
|
||||
|
||||
@FormUrlEncoded
|
||||
@PUT
|
||||
Observable<GenericOverall> setLobbyForConversation(@Header("Authorization") String authorization,
|
||||
@Url String url, @Field("viewState") Integer state,
|
||||
@Field("timer") Long timer);
|
||||
}
|
||||
|
@ -29,7 +29,6 @@ import androidx.emoji.bundled.BundledEmojiCompatConfig
|
||||
import androidx.emoji.text.EmojiCompat
|
||||
import androidx.lifecycle.LifecycleObserver
|
||||
import androidx.multidex.MultiDex
|
||||
import androidx.multidex.MultiDexApplication
|
||||
import androidx.work.ExistingPeriodicWorkPolicy
|
||||
import androidx.work.OneTimeWorkRequest
|
||||
import androidx.work.PeriodicWorkRequest
|
||||
@ -54,7 +53,6 @@ import com.nextcloud.talk.newarch.di.module.NetworkModule
|
||||
import com.nextcloud.talk.newarch.di.module.StorageModule
|
||||
import com.nextcloud.talk.newarch.features.conversationsList.di.module.ConversationsListModule
|
||||
import com.nextcloud.talk.utils.ClosedInterfaceImpl
|
||||
import com.nextcloud.talk.utils.DeviceUtils
|
||||
import com.nextcloud.talk.utils.DisplayUtils
|
||||
import com.nextcloud.talk.utils.OkHttpNetworkFetcherWithCache
|
||||
import com.nextcloud.talk.utils.database.arbitrarystorage.ArbitraryStorageModule
|
||||
@ -78,150 +76,174 @@ import java.util.concurrent.TimeUnit
|
||||
import javax.inject.Inject
|
||||
import javax.inject.Singleton
|
||||
|
||||
@AutoComponent(modules = [BusModule::class, ContextModule::class, DatabaseModule::class, RestModule::class, UserModule::class, ArbitraryStorageModule::class])
|
||||
@AutoComponent(
|
||||
modules = [BusModule::class, ContextModule::class, DatabaseModule::class, RestModule::class, UserModule::class, ArbitraryStorageModule::class]
|
||||
)
|
||||
@Singleton
|
||||
@AutoInjector(NextcloudTalkApplication::class)
|
||||
class NextcloudTalkApplication : Application(), LifecycleObserver {
|
||||
//region Fields (components)
|
||||
lateinit var componentApplication: NextcloudTalkApplicationComponent
|
||||
private set
|
||||
//endregion
|
||||
//region Fields (components)
|
||||
lateinit var componentApplication: NextcloudTalkApplicationComponent
|
||||
private set
|
||||
//endregion
|
||||
|
||||
//region Getters
|
||||
//region Getters
|
||||
|
||||
@Inject
|
||||
lateinit var appPreferences: AppPreferences
|
||||
@Inject
|
||||
lateinit var okHttpClient: OkHttpClient
|
||||
//endregion
|
||||
@Inject
|
||||
lateinit var appPreferences: AppPreferences
|
||||
@Inject
|
||||
lateinit var okHttpClient: OkHttpClient
|
||||
//endregion
|
||||
|
||||
//region private methods
|
||||
private fun initializeWebRtc() {
|
||||
try {
|
||||
if (MagicWebRTCUtils.HARDWARE_AEC_BLACKLIST.contains(Build.MODEL)) {
|
||||
WebRtcAudioUtils.setWebRtcBasedAcousticEchoCanceler(true)
|
||||
}
|
||||
//region private methods
|
||||
private fun initializeWebRtc() {
|
||||
try {
|
||||
if (MagicWebRTCUtils.HARDWARE_AEC_BLACKLIST.contains(Build.MODEL)) {
|
||||
WebRtcAudioUtils.setWebRtcBasedAcousticEchoCanceler(true)
|
||||
}
|
||||
|
||||
if (!MagicWebRTCUtils.OPEN_SL_ES_WHITELIST.contains(Build.MODEL)) {
|
||||
WebRtcAudioManager.setBlacklistDeviceForOpenSLESUsage(true)
|
||||
}
|
||||
if (!MagicWebRTCUtils.OPEN_SL_ES_WHITELIST.contains(Build.MODEL)) {
|
||||
WebRtcAudioManager.setBlacklistDeviceForOpenSLESUsage(true)
|
||||
}
|
||||
|
||||
|
||||
PeerConnectionFactory.initialize(PeerConnectionFactory.InitializationOptions.builder(this)
|
||||
.setEnableVideoHwAcceleration(MagicWebRTCUtils.shouldEnableVideoHardwareAcceleration())
|
||||
.createInitializationOptions())
|
||||
} catch (e: UnsatisfiedLinkError) {
|
||||
Log.w(TAG, e)
|
||||
}
|
||||
|
||||
PeerConnectionFactory.initialize(
|
||||
PeerConnectionFactory.InitializationOptions.builder(this)
|
||||
.setEnableVideoHwAcceleration(
|
||||
MagicWebRTCUtils.shouldEnableVideoHardwareAcceleration()
|
||||
)
|
||||
.createInitializationOptions()
|
||||
)
|
||||
} catch (e: UnsatisfiedLinkError) {
|
||||
Log.w(TAG, e)
|
||||
}
|
||||
|
||||
//endregion
|
||||
}
|
||||
|
||||
//region Overridden methods
|
||||
override fun onCreate() {
|
||||
sharedApplication = this
|
||||
//endregion
|
||||
|
||||
val securityKeyManager = SecurityKeyManager.getInstance()
|
||||
val securityKeyConfig = SecurityKeyManagerConfig.Builder()
|
||||
.setEnableDebugLogging(BuildConfig.DEBUG)
|
||||
//region Overridden methods
|
||||
override fun onCreate() {
|
||||
sharedApplication = this
|
||||
|
||||
val securityKeyManager = SecurityKeyManager.getInstance()
|
||||
val securityKeyConfig = SecurityKeyManagerConfig.Builder()
|
||||
.setEnableDebugLogging(BuildConfig.DEBUG)
|
||||
.build()
|
||||
securityKeyManager.init(this, securityKeyConfig)
|
||||
|
||||
initializeWebRtc()
|
||||
DisplayUtils.useCompatVectorIfNeeded()
|
||||
buildComponent()
|
||||
DavUtils.registerCustomFactories()
|
||||
|
||||
componentApplication.inject(this)
|
||||
|
||||
setAppTheme(appPreferences.theme)
|
||||
super.onCreate()
|
||||
|
||||
val imagePipelineConfig = ImagePipelineConfig.newBuilder(this)
|
||||
.setNetworkFetcher(OkHttpNetworkFetcherWithCache(okHttpClient))
|
||||
.setMainDiskCacheConfig(
|
||||
DiskCacheConfig.newBuilder(this)
|
||||
.setMaxCacheSize(0)
|
||||
.setMaxCacheSizeOnLowDiskSpace(0)
|
||||
.setMaxCacheSizeOnVeryLowDiskSpace(0)
|
||||
.build()
|
||||
securityKeyManager.init(this, securityKeyConfig)
|
||||
)
|
||||
.build()
|
||||
|
||||
initializeWebRtc()
|
||||
DisplayUtils.useCompatVectorIfNeeded()
|
||||
buildComponent()
|
||||
DavUtils.registerCustomFactories()
|
||||
Fresco.initialize(this, imagePipelineConfig)
|
||||
Security.insertProviderAt(Conscrypt.newProvider(), 1)
|
||||
|
||||
componentApplication.inject(this)
|
||||
ClosedInterfaceImpl().providerInstallerInstallIfNeededAsync()
|
||||
|
||||
setAppTheme(appPreferences.theme)
|
||||
super.onCreate()
|
||||
val pushRegistrationWork = OneTimeWorkRequest.Builder(PushRegistrationWorker::class.java)
|
||||
.build()
|
||||
val accountRemovalWork = OneTimeWorkRequest.Builder(AccountRemovalWorker::class.java)
|
||||
.build()
|
||||
val periodicCapabilitiesUpdateWork = PeriodicWorkRequest.Builder(
|
||||
CapabilitiesWorker::class.java,
|
||||
12, TimeUnit.HOURS
|
||||
)
|
||||
.build()
|
||||
val capabilitiesUpdateWork = OneTimeWorkRequest.Builder(CapabilitiesWorker::class.java)
|
||||
.build()
|
||||
val signalingSettingsWork = OneTimeWorkRequest.Builder(SignalingSettingsWorker::class.java)
|
||||
.build()
|
||||
|
||||
val imagePipelineConfig = ImagePipelineConfig.newBuilder(this)
|
||||
.setNetworkFetcher(OkHttpNetworkFetcherWithCache(okHttpClient))
|
||||
.setMainDiskCacheConfig(DiskCacheConfig.newBuilder(this)
|
||||
.setMaxCacheSize(0)
|
||||
.setMaxCacheSizeOnLowDiskSpace(0)
|
||||
.setMaxCacheSizeOnVeryLowDiskSpace(0)
|
||||
.build())
|
||||
.build()
|
||||
WorkManager.getInstance()
|
||||
.enqueue(pushRegistrationWork)
|
||||
WorkManager.getInstance()
|
||||
.enqueue(accountRemovalWork)
|
||||
WorkManager.getInstance()
|
||||
.enqueue(capabilitiesUpdateWork)
|
||||
WorkManager.getInstance()
|
||||
.enqueue(signalingSettingsWork)
|
||||
WorkManager.getInstance()
|
||||
.enqueueUniquePeriodicWork(
|
||||
"DailyCapabilitiesUpdateWork", ExistingPeriodicWorkPolicy.REPLACE,
|
||||
periodicCapabilitiesUpdateWork
|
||||
)
|
||||
|
||||
Fresco.initialize(this, imagePipelineConfig)
|
||||
Security.insertProviderAt(Conscrypt.newProvider(), 1)
|
||||
val config = BundledEmojiCompatConfig(this)
|
||||
config.setReplaceAll(true)
|
||||
val emojiCompat = EmojiCompat.init(config)
|
||||
|
||||
ClosedInterfaceImpl().providerInstallerInstallIfNeededAsync()
|
||||
EmojiManager.install(GoogleCompatEmojiProvider(emojiCompat))
|
||||
}
|
||||
|
||||
val pushRegistrationWork = OneTimeWorkRequest.Builder(PushRegistrationWorker::class.java).build()
|
||||
val accountRemovalWork = OneTimeWorkRequest.Builder(AccountRemovalWorker::class.java).build()
|
||||
val periodicCapabilitiesUpdateWork = PeriodicWorkRequest.Builder(CapabilitiesWorker::class.java,
|
||||
12, TimeUnit.HOURS).build()
|
||||
val capabilitiesUpdateWork = OneTimeWorkRequest.Builder(CapabilitiesWorker::class.java).build()
|
||||
val signalingSettingsWork = OneTimeWorkRequest.Builder(SignalingSettingsWorker::class.java).build()
|
||||
override fun onTerminate() {
|
||||
super.onTerminate()
|
||||
sharedApplication = null
|
||||
}
|
||||
//endregion
|
||||
|
||||
WorkManager.getInstance().enqueue(pushRegistrationWork)
|
||||
WorkManager.getInstance().enqueue(accountRemovalWork)
|
||||
WorkManager.getInstance().enqueue(capabilitiesUpdateWork)
|
||||
WorkManager.getInstance().enqueue(signalingSettingsWork)
|
||||
WorkManager.getInstance().enqueueUniquePeriodicWork("DailyCapabilitiesUpdateWork", ExistingPeriodicWorkPolicy.REPLACE, periodicCapabilitiesUpdateWork)
|
||||
//region Protected methods
|
||||
protected fun buildComponent() {
|
||||
componentApplication = DaggerNextcloudTalkApplicationComponent.builder()
|
||||
.busModule(BusModule())
|
||||
.contextModule(ContextModule(applicationContext))
|
||||
.databaseModule(DatabaseModule())
|
||||
.restModule(RestModule(applicationContext))
|
||||
.userModule(UserModule())
|
||||
.arbitraryStorageModule(ArbitraryStorageModule())
|
||||
.build()
|
||||
|
||||
val config = BundledEmojiCompatConfig(this)
|
||||
config.setReplaceAll(true)
|
||||
val emojiCompat = EmojiCompat.init(config)
|
||||
|
||||
EmojiManager.install(GoogleCompatEmojiProvider(emojiCompat))
|
||||
startKoin {
|
||||
androidContext(this@NextcloudTalkApplication)
|
||||
androidLogger()
|
||||
modules(listOf(CommunicationModule, StorageModule, NetworkModule, ConversationsListModule))
|
||||
}
|
||||
}
|
||||
|
||||
override fun onTerminate() {
|
||||
super.onTerminate()
|
||||
sharedApplication = null
|
||||
}
|
||||
override fun attachBaseContext(base: Context) {
|
||||
super.attachBaseContext(base)
|
||||
MultiDex.install(this)
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = NextcloudTalkApplication::class.java.simpleName
|
||||
//region Singleton
|
||||
//endregion
|
||||
|
||||
|
||||
//region Protected methods
|
||||
protected fun buildComponent() {
|
||||
componentApplication = DaggerNextcloudTalkApplicationComponent.builder()
|
||||
.busModule(BusModule())
|
||||
.contextModule(ContextModule(applicationContext))
|
||||
.databaseModule(DatabaseModule())
|
||||
.restModule(RestModule(applicationContext))
|
||||
.userModule(UserModule())
|
||||
.arbitraryStorageModule(ArbitraryStorageModule())
|
||||
.build()
|
||||
|
||||
startKoin {
|
||||
androidContext(this@NextcloudTalkApplication)
|
||||
androidLogger()
|
||||
modules(listOf(CommunicationModule, StorageModule, NetworkModule, ConversationsListModule))
|
||||
}
|
||||
}
|
||||
|
||||
override fun attachBaseContext(base: Context) {
|
||||
super.attachBaseContext(base)
|
||||
MultiDex.install(this)
|
||||
}
|
||||
|
||||
companion object {
|
||||
private val TAG = NextcloudTalkApplication::class.java.simpleName
|
||||
//region Singleton
|
||||
//endregion
|
||||
|
||||
var sharedApplication: NextcloudTalkApplication? = null
|
||||
protected set
|
||||
//endregion
|
||||
|
||||
//region Setters
|
||||
fun setAppTheme(theme: String) {
|
||||
when (theme) {
|
||||
"night_no" -> AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_NO)
|
||||
"night_yes" -> AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_YES)
|
||||
"battery_saver" -> AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_AUTO_BATTERY)
|
||||
else ->
|
||||
// will be "follow_system" only for now
|
||||
AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_FOLLOW_SYSTEM)
|
||||
}
|
||||
}
|
||||
}
|
||||
var sharedApplication: NextcloudTalkApplication? = null
|
||||
protected set
|
||||
//endregion
|
||||
|
||||
//region Setters
|
||||
fun setAppTheme(theme: String) {
|
||||
when (theme) {
|
||||
"night_no" -> AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_NO)
|
||||
"night_yes" -> AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_YES)
|
||||
"battery_saver" -> AppCompatDelegate.setDefaultNightMode(
|
||||
AppCompatDelegate.MODE_NIGHT_AUTO_BATTERY
|
||||
)
|
||||
else ->
|
||||
// will be "follow_system" only for now
|
||||
AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_FOLLOW_SYSTEM)
|
||||
}
|
||||
}
|
||||
}
|
||||
//endregion
|
||||
}
|
||||
|
@ -25,9 +25,9 @@ import android.text.Editable;
|
||||
import android.text.Spanned;
|
||||
import android.widget.EditText;
|
||||
import com.facebook.widget.text.span.BetterImageSpan;
|
||||
import com.nextcloud.talk.models.json.mention.Mention;
|
||||
import com.nextcloud.talk.R;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.models.json.mention.Mention;
|
||||
import com.nextcloud.talk.utils.DisplayUtils;
|
||||
import com.nextcloud.talk.utils.MagicCharPolicy;
|
||||
import com.nextcloud.talk.utils.text.Spans;
|
||||
@ -36,44 +36,44 @@ import com.vanniktech.emoji.EmojiRange;
|
||||
import com.vanniktech.emoji.EmojiUtils;
|
||||
|
||||
public class MentionAutocompleteCallback implements AutocompleteCallback<Mention> {
|
||||
private Context context;
|
||||
private UserEntity conversationUser;
|
||||
private EditText editText;
|
||||
private Context context;
|
||||
private UserEntity conversationUser;
|
||||
private EditText editText;
|
||||
|
||||
public MentionAutocompleteCallback(Context context, UserEntity conversationUser,
|
||||
EditText editText) {
|
||||
this.context = context;
|
||||
this.conversationUser = conversationUser;
|
||||
this.editText = editText;
|
||||
public MentionAutocompleteCallback(Context context, UserEntity conversationUser,
|
||||
EditText editText) {
|
||||
this.context = context;
|
||||
this.conversationUser = conversationUser;
|
||||
this.editText = editText;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onPopupItemClicked(Editable editable, Mention item) {
|
||||
int[] range = MagicCharPolicy.getQueryRange(editable);
|
||||
if (range == null) return false;
|
||||
int start = range[0];
|
||||
int end = range[1];
|
||||
String replacement = item.getLabel();
|
||||
|
||||
StringBuilder replacementStringBuilder = new StringBuilder(item.getLabel());
|
||||
for (EmojiRange emojiRange : EmojiUtils.emojis(replacement)) {
|
||||
replacementStringBuilder.delete(emojiRange.start, emojiRange.end);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onPopupItemClicked(Editable editable, Mention item) {
|
||||
int[] range = MagicCharPolicy.getQueryRange(editable);
|
||||
if (range == null) return false;
|
||||
int start = range[0];
|
||||
int end = range[1];
|
||||
String replacement = item.getLabel();
|
||||
editable.replace(start, end, replacementStringBuilder.toString() + " ");
|
||||
Spans.MentionChipSpan mentionChipSpan =
|
||||
new Spans.MentionChipSpan(DisplayUtils.getDrawableForMentionChipSpan(context,
|
||||
item.getId(), item.getLabel(), conversationUser, item.getSource(),
|
||||
R.xml.chip_you, editText),
|
||||
BetterImageSpan.ALIGN_CENTER,
|
||||
item.getId(), item.getLabel());
|
||||
editable.setSpan(mentionChipSpan, start, start + replacementStringBuilder.toString().length(),
|
||||
Spanned.SPAN_INCLUSIVE_INCLUSIVE);
|
||||
return true;
|
||||
}
|
||||
|
||||
StringBuilder replacementStringBuilder = new StringBuilder(item.getLabel());
|
||||
for(EmojiRange emojiRange : EmojiUtils.emojis(replacement)) {
|
||||
replacementStringBuilder.delete(emojiRange.start, emojiRange.end);
|
||||
}
|
||||
@Override
|
||||
public void onPopupVisibilityChanged(boolean shown) {
|
||||
|
||||
editable.replace(start, end, replacementStringBuilder.toString() + " ");
|
||||
Spans.MentionChipSpan mentionChipSpan =
|
||||
new Spans.MentionChipSpan(DisplayUtils.getDrawableForMentionChipSpan(context,
|
||||
item.getId(), item.getLabel(), conversationUser, item.getSource(),
|
||||
R.xml.chip_you, editText),
|
||||
BetterImageSpan.ALIGN_CENTER,
|
||||
item.getId(), item.getLabel());
|
||||
editable.setSpan(mentionChipSpan, start, start + replacementStringBuilder.toString().length(),
|
||||
Spanned.SPAN_INCLUSIVE_INCLUSIVE);
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPopupVisibilityChanged(boolean shown) {
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -50,136 +50,143 @@ import java.util.List;
|
||||
import javax.inject.Inject;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class BrowserFileItem extends AbstractFlexibleItem<BrowserFileItem.ViewHolder> implements IFilterable<String> {
|
||||
@Inject
|
||||
Context context;
|
||||
private BrowserFile browserFile;
|
||||
private UserEntity activeUser;
|
||||
private SelectionInterface selectionInterface;
|
||||
private boolean selected;
|
||||
public class BrowserFileItem extends AbstractFlexibleItem<BrowserFileItem.ViewHolder>
|
||||
implements IFilterable<String> {
|
||||
@Inject
|
||||
Context context;
|
||||
private BrowserFile browserFile;
|
||||
private UserEntity activeUser;
|
||||
private SelectionInterface selectionInterface;
|
||||
private boolean selected;
|
||||
|
||||
public BrowserFileItem(BrowserFile browserFile, UserEntity activeUser, SelectionInterface selectionInterface) {
|
||||
this.browserFile = browserFile;
|
||||
this.activeUser = activeUser;
|
||||
this.selectionInterface = selectionInterface;
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
public BrowserFileItem(BrowserFile browserFile, UserEntity activeUser,
|
||||
SelectionInterface selectionInterface) {
|
||||
this.browserFile = browserFile;
|
||||
this.activeUser = activeUser;
|
||||
this.selectionInterface = selectionInterface;
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof BrowserFileItem) {
|
||||
BrowserFileItem inItem = (BrowserFileItem) o;
|
||||
return browserFile.getPath().equals(inItem.getModel().getPath());
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof BrowserFileItem) {
|
||||
BrowserFileItem inItem = (BrowserFileItem) o;
|
||||
return browserFile.getPath().equals(inItem.getModel().getPath());
|
||||
return false;
|
||||
}
|
||||
|
||||
public BrowserFile getModel() {
|
||||
return browserFile;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_browser_file;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ViewHolder createViewHolder(View view, FlexibleAdapter<IFlexible> adapter) {
|
||||
return new ViewHolder(view, adapter);
|
||||
}
|
||||
|
||||
private boolean isSelected() {
|
||||
return selected;
|
||||
}
|
||||
|
||||
private void setSelected(boolean selected) {
|
||||
this.selected = selected;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, ViewHolder holder, int position,
|
||||
List<Object> payloads) {
|
||||
holder.fileIconImageView.setController(null);
|
||||
|
||||
if (browserFile.isEncrypted()) {
|
||||
holder.fileEncryptedImageView.setVisibility(View.VISIBLE);
|
||||
holder.itemView.setEnabled(false);
|
||||
holder.itemView.setAlpha(0.38f);
|
||||
} else {
|
||||
holder.fileEncryptedImageView.setVisibility(View.GONE);
|
||||
holder.itemView.setEnabled(true);
|
||||
holder.itemView.setAlpha(1.0f);
|
||||
}
|
||||
|
||||
if (browserFile.isFavorite()) {
|
||||
holder.fileFavoriteImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.fileFavoriteImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
holder.fileIconImageView.getHierarchy()
|
||||
.setPlaceholderImage(context.getDrawable(
|
||||
DrawableUtils.INSTANCE.getDrawableResourceIdForMimeType(browserFile.getMimeType())));
|
||||
|
||||
if (browserFile.isHasPreview()) {
|
||||
String path = ApiUtils.getUrlForFilePreviewWithRemotePath(activeUser.getBaseUrl(),
|
||||
browserFile.getPath(),
|
||||
context.getResources().getDimensionPixelSize(R.dimen.small_item_height));
|
||||
|
||||
if (path.length() > 0) {
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(path, null))
|
||||
.build();
|
||||
holder.fileIconImageView.setController(draweeController);
|
||||
}
|
||||
}
|
||||
|
||||
holder.filenameTextView.setText(browserFile.getDisplayName());
|
||||
holder.fileModifiedTextView.setText(String.format(context.getString(R.string.nc_last_modified),
|
||||
Formatter.formatShortFileSize(context, browserFile.getSize()),
|
||||
DateUtils.INSTANCE.getLocalDateTimeStringFromTimestamp(
|
||||
browserFile.getModifiedTimestamp())));
|
||||
setSelected(selectionInterface.isPathSelected(browserFile.getPath()));
|
||||
holder.selectFileCheckbox.setChecked(isSelected());
|
||||
|
||||
if (!browserFile.isEncrypted()) {
|
||||
holder.selectFileCheckbox.setOnClickListener(new View.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
if (((CheckBox) v).isChecked() != isSelected()) {
|
||||
setSelected(((CheckBox) v).isChecked());
|
||||
selectionInterface.toggleBrowserItemSelection(browserFile.getPath());
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
});
|
||||
}
|
||||
|
||||
public BrowserFile getModel() {
|
||||
return browserFile;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getLayoutRes() {
|
||||
return R.layout.rv_item_browser_file;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ViewHolder createViewHolder(View view, FlexibleAdapter<IFlexible> adapter) {
|
||||
return new ViewHolder(view, adapter);
|
||||
|
||||
}
|
||||
|
||||
private boolean isSelected() {
|
||||
return selected;
|
||||
}
|
||||
|
||||
private void setSelected(boolean selected) {
|
||||
this.selected = selected;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bindViewHolder(FlexibleAdapter<IFlexible> adapter, ViewHolder holder, int position, List<Object> payloads) {
|
||||
holder.fileIconImageView.setController(null);
|
||||
|
||||
if (browserFile.isEncrypted()) {
|
||||
holder.fileEncryptedImageView.setVisibility(View.VISIBLE);
|
||||
holder.itemView.setEnabled(false);
|
||||
holder.itemView.setAlpha(0.38f);
|
||||
} else {
|
||||
holder.fileEncryptedImageView.setVisibility(View.GONE);
|
||||
holder.itemView.setEnabled(true);
|
||||
holder.itemView.setAlpha(1.0f);
|
||||
}
|
||||
|
||||
if (browserFile.isFavorite()) {
|
||||
holder.fileFavoriteImageView.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
holder.fileFavoriteImageView.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
holder.fileIconImageView.getHierarchy().setPlaceholderImage(context.getDrawable(DrawableUtils.INSTANCE.getDrawableResourceIdForMimeType(browserFile.getMimeType())));
|
||||
|
||||
if (browserFile.isHasPreview()) {
|
||||
String path = ApiUtils.getUrlForFilePreviewWithRemotePath(activeUser.getBaseUrl(),
|
||||
browserFile.getPath(),
|
||||
context.getResources().getDimensionPixelSize(R.dimen.small_item_height));
|
||||
|
||||
if (path.length() > 0) {
|
||||
DraweeController draweeController = Fresco.newDraweeControllerBuilder()
|
||||
.setAutoPlayAnimations(true)
|
||||
.setImageRequest(DisplayUtils.getImageRequestForUrl(path, null))
|
||||
.build();
|
||||
holder.fileIconImageView.setController(draweeController);
|
||||
}
|
||||
}
|
||||
|
||||
holder.filenameTextView.setText(browserFile.getDisplayName());
|
||||
holder.fileModifiedTextView.setText(String.format(context.getString(R.string.nc_last_modified),
|
||||
Formatter.formatShortFileSize(context, browserFile.getSize()),
|
||||
DateUtils.INSTANCE.getLocalDateTimeStringFromTimestamp(browserFile.getModifiedTimestamp())));
|
||||
setSelected(selectionInterface.isPathSelected(browserFile.getPath()));
|
||||
holder.selectFileCheckbox.setChecked(isSelected());
|
||||
|
||||
if (!browserFile.isEncrypted()) {
|
||||
holder.selectFileCheckbox.setOnClickListener(new View.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
if (((CheckBox) v).isChecked() != isSelected()) {
|
||||
setSelected(((CheckBox) v).isChecked());
|
||||
selectionInterface.toggleBrowserItemSelection(browserFile.getPath());
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
holder.filenameTextView.setSelected(true);
|
||||
holder.fileModifiedTextView.setSelected(true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return false;
|
||||
}
|
||||
|
||||
static class ViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.file_icon)
|
||||
public SimpleDraweeView fileIconImageView;
|
||||
@BindView(R.id.file_modified_info)
|
||||
public TextView fileModifiedTextView;
|
||||
@BindView(R.id.filename_text_view)
|
||||
public TextView filenameTextView;
|
||||
@BindView(R.id.select_file_checkbox)
|
||||
public CheckBox selectFileCheckbox;
|
||||
@BindView(R.id.fileEncryptedImageView)
|
||||
public ImageView fileEncryptedImageView;
|
||||
@BindView(R.id.fileFavoriteImageView)
|
||||
public ImageView fileFavoriteImageView;
|
||||
|
||||
ViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
holder.filenameTextView.setSelected(true);
|
||||
holder.fileModifiedTextView.setSelected(true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean filter(String constraint) {
|
||||
return false;
|
||||
}
|
||||
|
||||
static class ViewHolder extends FlexibleViewHolder {
|
||||
|
||||
@BindView(R.id.file_icon)
|
||||
public SimpleDraweeView fileIconImageView;
|
||||
@BindView(R.id.file_modified_info)
|
||||
public TextView fileModifiedTextView;
|
||||
@BindView(R.id.filename_text_view)
|
||||
public TextView filenameTextView;
|
||||
@BindView(R.id.select_file_checkbox)
|
||||
public CheckBox selectFileCheckbox;
|
||||
@BindView(R.id.fileEncryptedImageView)
|
||||
public ImageView fileEncryptedImageView;
|
||||
@BindView(R.id.fileFavoriteImageView)
|
||||
public ImageView fileFavoriteImageView;
|
||||
|
||||
ViewHolder(View view, FlexibleAdapter adapter) {
|
||||
super(view, adapter);
|
||||
ButterKnife.bind(this, view);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -71,278 +71,281 @@ import org.parceler.Parcels;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class BrowserController extends BaseController implements ListingInterface,
|
||||
FlexibleAdapter.OnItemClickListener, SelectionInterface {
|
||||
private final Set<String> selectedPaths;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@BindView(R.id.recyclerView)
|
||||
RecyclerView recyclerView;
|
||||
@BindView(R.id.fast_scroller)
|
||||
FastScroller fastScroller;
|
||||
@BindView(R.id.action_back)
|
||||
BottomNavigationItemView backMenuItem;
|
||||
@BindView(R.id.action_refresh)
|
||||
BottomNavigationItemView actionRefreshMenuItem;
|
||||
@Inject
|
||||
Context context;
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
FlexibleAdapter.OnItemClickListener, SelectionInterface {
|
||||
private final Set<String> selectedPaths;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@BindView(R.id.recyclerView)
|
||||
RecyclerView recyclerView;
|
||||
@BindView(R.id.fast_scroller)
|
||||
FastScroller fastScroller;
|
||||
@BindView(R.id.action_back)
|
||||
BottomNavigationItemView backMenuItem;
|
||||
@BindView(R.id.action_refresh)
|
||||
BottomNavigationItemView actionRefreshMenuItem;
|
||||
@Inject
|
||||
Context context;
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
|
||||
private MenuItem filesSelectionDoneMenuItem;
|
||||
private RecyclerView.LayoutManager layoutManager;
|
||||
private MenuItem filesSelectionDoneMenuItem;
|
||||
private RecyclerView.LayoutManager layoutManager;
|
||||
|
||||
private FlexibleAdapter<AbstractFlexibleItem> adapter;
|
||||
private List<AbstractFlexibleItem> recyclerViewItems = new ArrayList<>();
|
||||
private FlexibleAdapter<AbstractFlexibleItem> adapter;
|
||||
private List<AbstractFlexibleItem> recyclerViewItems = new ArrayList<>();
|
||||
|
||||
private ListingAbstractClass listingAbstractClass;
|
||||
private BrowserType browserType;
|
||||
private String currentPath;
|
||||
private UserEntity activeUser;
|
||||
private String roomToken;
|
||||
private ListingAbstractClass listingAbstractClass;
|
||||
private BrowserType browserType;
|
||||
private String currentPath;
|
||||
private UserEntity activeUser;
|
||||
private String roomToken;
|
||||
|
||||
public BrowserController(Bundle args) {
|
||||
super();
|
||||
setHasOptionsMenu(true);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
browserType = Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_BROWSER_TYPE()));
|
||||
activeUser = Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_USER_ENTITY()));
|
||||
roomToken = args.getString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN());
|
||||
public BrowserController(Bundle args) {
|
||||
super();
|
||||
setHasOptionsMenu(true);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
browserType = Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_BROWSER_TYPE()));
|
||||
activeUser = Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_USER_ENTITY()));
|
||||
roomToken = args.getString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN());
|
||||
|
||||
currentPath = "/";
|
||||
if (BrowserType.DAV_BROWSER.equals(browserType)) {
|
||||
listingAbstractClass = new DavListing(this);
|
||||
} else {
|
||||
//listingAbstractClass = new LocalListing(this);
|
||||
currentPath = "/";
|
||||
if (BrowserType.DAV_BROWSER.equals(browserType)) {
|
||||
listingAbstractClass = new DavListing(this);
|
||||
} else {
|
||||
//listingAbstractClass = new LocalListing(this);
|
||||
}
|
||||
|
||||
selectedPaths = Collections.synchronizedSet(new TreeSet<>());
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_browser, container, false);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
if (adapter == null) {
|
||||
adapter = new FlexibleAdapter<>(recyclerViewItems, context, false);
|
||||
}
|
||||
|
||||
changeEnabledStatusForBarItems(true);
|
||||
prepareViews();
|
||||
}
|
||||
|
||||
private void onFileSelectionDone() {
|
||||
synchronized (selectedPaths) {
|
||||
Iterator<String> iterator = selectedPaths.iterator();
|
||||
|
||||
List<String> paths = new ArrayList<>();
|
||||
Data data;
|
||||
OneTimeWorkRequest shareWorker;
|
||||
|
||||
while (iterator.hasNext()) {
|
||||
String path = iterator.next();
|
||||
paths.add(path);
|
||||
iterator.remove();
|
||||
if (paths.size() == 10 || !iterator.hasNext()) {
|
||||
data = new Data.Builder()
|
||||
.putLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), activeUser.getId())
|
||||
.putString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN(), roomToken)
|
||||
.putStringArray(BundleKeys.INSTANCE.getKEY_FILE_PATHS(), paths.toArray(new String[0]))
|
||||
.build();
|
||||
shareWorker = new OneTimeWorkRequest.Builder(ShareOperationWorker.class)
|
||||
.setInputData(data)
|
||||
.build();
|
||||
WorkManager.getInstance().enqueue(shareWorker);
|
||||
paths = new ArrayList<>();
|
||||
}
|
||||
|
||||
selectedPaths = Collections.synchronizedSet(new TreeSet<>());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_browser, container, false);
|
||||
getRouter().popCurrentController();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
|
||||
super.onCreateOptionsMenu(menu, inflater);
|
||||
inflater.inflate(R.menu.menu_share_files, menu);
|
||||
filesSelectionDoneMenuItem = menu.findItem(R.id.files_selection_done);
|
||||
filesSelectionDoneMenuItem.setVisible(selectedPaths.size() > 0);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onOptionsItemSelected(@NonNull MenuItem item) {
|
||||
switch (item.getItemId()) {
|
||||
case R.id.files_selection_done:
|
||||
onFileSelectionDone();
|
||||
return true;
|
||||
default:
|
||||
return super.onOptionsItemSelected(item);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
refreshCurrentPath();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
super.onDestroy();
|
||||
listingAbstractClass.tearDown();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getTitle() {
|
||||
return currentPath;
|
||||
}
|
||||
|
||||
@OnClick(R.id.action_back)
|
||||
void goBack() {
|
||||
fetchPath(new File(currentPath).getParent());
|
||||
}
|
||||
|
||||
@OnClick(R.id.action_refresh)
|
||||
void refreshCurrentPath() {
|
||||
fetchPath(currentPath);
|
||||
}
|
||||
|
||||
@SuppressLint("RestrictedApi")
|
||||
private void changeEnabledStatusForBarItems(boolean shouldBeEnabled) {
|
||||
if (actionRefreshMenuItem != null) {
|
||||
actionRefreshMenuItem.setEnabled(shouldBeEnabled);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
if (adapter == null) {
|
||||
adapter = new FlexibleAdapter<>(recyclerViewItems, context, false);
|
||||
}
|
||||
if (backMenuItem != null) {
|
||||
backMenuItem.setEnabled(shouldBeEnabled && !currentPath.equals("/"));
|
||||
}
|
||||
}
|
||||
|
||||
changeEnabledStatusForBarItems(true);
|
||||
prepareViews();
|
||||
private void fetchPath(String path) {
|
||||
listingAbstractClass.cancelAllJobs();
|
||||
changeEnabledStatusForBarItems(false);
|
||||
|
||||
listingAbstractClass.getFiles(path, activeUser,
|
||||
BrowserType.DAV_BROWSER.equals(browserType) ? okHttpClient : null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void listingResult(DavResponse davResponse) {
|
||||
adapter.clear();
|
||||
List<AbstractFlexibleItem> fileBrowserItems = new ArrayList<>();
|
||||
if (davResponse.getData() != null) {
|
||||
final List<BrowserFile> objectList = (List<BrowserFile>) davResponse.getData();
|
||||
|
||||
currentPath = objectList.get(0).getPath();
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> setTitle());
|
||||
}
|
||||
|
||||
for (int i = 1; i < objectList.size(); i++) {
|
||||
fileBrowserItems.add(new BrowserFileItem(objectList.get(i), activeUser, this));
|
||||
}
|
||||
}
|
||||
|
||||
private void onFileSelectionDone() {
|
||||
synchronized (selectedPaths) {
|
||||
Iterator<String> iterator = selectedPaths.iterator();
|
||||
|
||||
List<String> paths = new ArrayList<>();
|
||||
Data data;
|
||||
OneTimeWorkRequest shareWorker;
|
||||
|
||||
while (iterator.hasNext()) {
|
||||
String path = iterator.next();
|
||||
paths.add(path);
|
||||
iterator.remove();
|
||||
if (paths.size() == 10 || !iterator.hasNext()) {
|
||||
data = new Data.Builder()
|
||||
.putLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), activeUser.getId())
|
||||
.putString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN(), roomToken)
|
||||
.putStringArray(BundleKeys.INSTANCE.getKEY_FILE_PATHS(), paths.toArray(new String[0]))
|
||||
.build();
|
||||
shareWorker = new OneTimeWorkRequest.Builder(ShareOperationWorker.class)
|
||||
.setInputData(data)
|
||||
.build();
|
||||
WorkManager.getInstance().enqueue(shareWorker);
|
||||
paths = new ArrayList<>();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
getRouter().popCurrentController();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
|
||||
super.onCreateOptionsMenu(menu, inflater);
|
||||
inflater.inflate(R.menu.menu_share_files, menu);
|
||||
filesSelectionDoneMenuItem = menu.findItem(R.id.files_selection_done);
|
||||
filesSelectionDoneMenuItem.setVisible(selectedPaths.size() > 0);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onOptionsItemSelected(@NonNull MenuItem item) {
|
||||
switch (item.getItemId()) {
|
||||
case R.id.files_selection_done:
|
||||
onFileSelectionDone();
|
||||
return true;
|
||||
default:
|
||||
return super.onOptionsItemSelected(item);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
refreshCurrentPath();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
super.onDestroy();
|
||||
listingAbstractClass.tearDown();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getTitle() {
|
||||
return currentPath;
|
||||
}
|
||||
|
||||
@OnClick(R.id.action_back)
|
||||
void goBack() {
|
||||
fetchPath(new File(currentPath).getParent());
|
||||
}
|
||||
|
||||
@OnClick(R.id.action_refresh)
|
||||
void refreshCurrentPath() {
|
||||
fetchPath(currentPath);
|
||||
}
|
||||
|
||||
@SuppressLint("RestrictedApi")
|
||||
private void changeEnabledStatusForBarItems(boolean shouldBeEnabled) {
|
||||
if (actionRefreshMenuItem != null) {
|
||||
actionRefreshMenuItem.setEnabled(shouldBeEnabled);
|
||||
}
|
||||
|
||||
if (backMenuItem != null) {
|
||||
backMenuItem.setEnabled(shouldBeEnabled && !currentPath.equals("/"));
|
||||
}
|
||||
}
|
||||
|
||||
private void fetchPath(String path) {
|
||||
listingAbstractClass.cancelAllJobs();
|
||||
changeEnabledStatusForBarItems(false);
|
||||
|
||||
listingAbstractClass.getFiles(path, activeUser, BrowserType.DAV_BROWSER.equals(browserType) ? okHttpClient : null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void listingResult(DavResponse davResponse) {
|
||||
adapter.clear();
|
||||
List<AbstractFlexibleItem> fileBrowserItems = new ArrayList<>();
|
||||
if (davResponse.getData() != null) {
|
||||
final List<BrowserFile> objectList = (List<BrowserFile>) davResponse.getData();
|
||||
|
||||
currentPath = objectList.get(0).getPath();
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> setTitle());
|
||||
}
|
||||
|
||||
for (int i = 1; i < objectList.size(); i++) {
|
||||
fileBrowserItems.add(new BrowserFileItem(objectList.get(i), activeUser, this));
|
||||
}
|
||||
}
|
||||
|
||||
adapter.addItems(0, fileBrowserItems);
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> {
|
||||
adapter.notifyDataSetChanged();
|
||||
changeEnabledStatusForBarItems(true);
|
||||
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
private boolean shouldPathBeSelectedDueToParent(String currentPath) {
|
||||
if (selectedPaths.size() > 0) {
|
||||
File file = new File(currentPath);
|
||||
if (!file.getParent().equals("/")) {
|
||||
while (file.getParent() != null) {
|
||||
String parent = file.getParent();
|
||||
if (new File(file.getParent()).getParent() != null) {
|
||||
parent += "/";
|
||||
}
|
||||
|
||||
if (selectedPaths.contains(parent)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
file = new File(file.getParent());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
private void checkAndRemoveAnySelectedParents(String currentPath) {
|
||||
File file = new File(currentPath);
|
||||
selectedPaths.remove(currentPath);
|
||||
while (file.getParent() != null) {
|
||||
selectedPaths.remove(file.getParent() + "/");
|
||||
file = new File(file.getParent());
|
||||
}
|
||||
adapter.addItems(0, fileBrowserItems);
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> {
|
||||
adapter.notifyDataSetChanged();
|
||||
changeEnabledStatusForBarItems(true);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onItemClick(View view, int position) {
|
||||
BrowserFile browserFile = ((BrowserFileItem) adapter.getItem(position)).getModel();
|
||||
if ("inode/directory".equals((browserFile.getMimeType()))) {
|
||||
fetchPath(browserFile.getPath());
|
||||
private boolean shouldPathBeSelectedDueToParent(String currentPath) {
|
||||
if (selectedPaths.size() > 0) {
|
||||
File file = new File(currentPath);
|
||||
if (!file.getParent().equals("/")) {
|
||||
while (file.getParent() != null) {
|
||||
String parent = file.getParent();
|
||||
if (new File(file.getParent()).getParent() != null) {
|
||||
parent += "/";
|
||||
}
|
||||
|
||||
if (selectedPaths.contains(parent)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
file = new File(file.getParent());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void prepareViews() {
|
||||
if (getActivity() != null) {
|
||||
layoutManager = new SmoothScrollLinearLayoutManager(getActivity());
|
||||
recyclerView.setLayoutManager(layoutManager);
|
||||
recyclerView.setHasFixedSize(true);
|
||||
recyclerView.setAdapter(adapter);
|
||||
return false;
|
||||
}
|
||||
|
||||
adapter.setFastScroller(fastScroller);
|
||||
adapter.addListener(this);
|
||||
|
||||
fastScroller.setBubbleTextCreator(position -> {
|
||||
IFlexible abstractFlexibleItem = adapter.getItem(position);
|
||||
if (abstractFlexibleItem instanceof BrowserFileItem) {
|
||||
return String.valueOf(((BrowserFileItem) adapter.getItem(position)).getModel().getDisplayName().charAt(0));
|
||||
} else {
|
||||
return "";
|
||||
}
|
||||
});
|
||||
}
|
||||
private void checkAndRemoveAnySelectedParents(String currentPath) {
|
||||
File file = new File(currentPath);
|
||||
selectedPaths.remove(currentPath);
|
||||
while (file.getParent() != null) {
|
||||
selectedPaths.remove(file.getParent() + "/");
|
||||
file = new File(file.getParent());
|
||||
}
|
||||
|
||||
@SuppressLint("RestrictedApi")
|
||||
@Override
|
||||
public void toggleBrowserItemSelection(String path) {
|
||||
if (selectedPaths.contains(path) || shouldPathBeSelectedDueToParent(path)) {
|
||||
checkAndRemoveAnySelectedParents(path);
|
||||
adapter.notifyDataSetChanged();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onItemClick(View view, int position) {
|
||||
BrowserFile browserFile = ((BrowserFileItem) adapter.getItem(position)).getModel();
|
||||
if ("inode/directory".equals((browserFile.getMimeType()))) {
|
||||
fetchPath(browserFile.getPath());
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
private void prepareViews() {
|
||||
if (getActivity() != null) {
|
||||
layoutManager = new SmoothScrollLinearLayoutManager(getActivity());
|
||||
recyclerView.setLayoutManager(layoutManager);
|
||||
recyclerView.setHasFixedSize(true);
|
||||
recyclerView.setAdapter(adapter);
|
||||
|
||||
adapter.setFastScroller(fastScroller);
|
||||
adapter.addListener(this);
|
||||
|
||||
fastScroller.setBubbleTextCreator(position -> {
|
||||
IFlexible abstractFlexibleItem = adapter.getItem(position);
|
||||
if (abstractFlexibleItem instanceof BrowserFileItem) {
|
||||
return String.valueOf(
|
||||
((BrowserFileItem) adapter.getItem(position)).getModel().getDisplayName().charAt(0));
|
||||
} else {
|
||||
// TOOD: if it's a folder, remove all the children we added manually
|
||||
selectedPaths.add(path);
|
||||
return "";
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
filesSelectionDoneMenuItem.setVisible(selectedPaths.size() > 0);
|
||||
@SuppressLint("RestrictedApi")
|
||||
@Override
|
||||
public void toggleBrowserItemSelection(String path) {
|
||||
if (selectedPaths.contains(path) || shouldPathBeSelectedDueToParent(path)) {
|
||||
checkAndRemoveAnySelectedParents(path);
|
||||
} else {
|
||||
// TOOD: if it's a folder, remove all the children we added manually
|
||||
selectedPaths.add(path);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isPathSelected(String path) {
|
||||
return (selectedPaths.contains(path) || shouldPathBeSelectedDueToParent(path));
|
||||
}
|
||||
filesSelectionDoneMenuItem.setVisible(selectedPaths.size() > 0);
|
||||
}
|
||||
|
||||
@Parcel
|
||||
public enum BrowserType {
|
||||
FILE_BROWSER,
|
||||
DAV_BROWSER,
|
||||
}
|
||||
@Override
|
||||
public boolean isPathSelected(String path) {
|
||||
return (selectedPaths.contains(path) || shouldPathBeSelectedDueToParent(path));
|
||||
}
|
||||
|
||||
@Parcel
|
||||
public enum BrowserType {
|
||||
FILE_BROWSER,
|
||||
DAV_BROWSER,
|
||||
}
|
||||
}
|
||||
|
@ -23,5 +23,5 @@ package com.nextcloud.talk.components.filebrowser.interfaces;
|
||||
import com.nextcloud.talk.components.filebrowser.models.DavResponse;
|
||||
|
||||
public interface ListingInterface {
|
||||
void listingResult(DavResponse davResponse);
|
||||
void listingResult(DavResponse davResponse);
|
||||
}
|
||||
|
@ -43,67 +43,68 @@ import org.parceler.Parcel;
|
||||
@JsonObject
|
||||
@Parcel
|
||||
public class BrowserFile {
|
||||
public String path;
|
||||
public String displayName;
|
||||
public String mimeType;
|
||||
public long modifiedTimestamp;
|
||||
public long size;
|
||||
public boolean isFile;
|
||||
// Used for remote files
|
||||
public String remoteId;
|
||||
public boolean hasPreview;
|
||||
public boolean favorite;
|
||||
public boolean encrypted;
|
||||
public String path;
|
||||
public String displayName;
|
||||
public String mimeType;
|
||||
public long modifiedTimestamp;
|
||||
public long size;
|
||||
public boolean isFile;
|
||||
// Used for remote files
|
||||
public String remoteId;
|
||||
public boolean hasPreview;
|
||||
public boolean favorite;
|
||||
public boolean encrypted;
|
||||
|
||||
public static BrowserFile getModelFromResponse(Response response, String remotePath) {
|
||||
BrowserFile browserFile = new BrowserFile();
|
||||
browserFile.setPath(Uri.decode(remotePath));
|
||||
browserFile.setDisplayName(Uri.decode(new File(remotePath).getName()));
|
||||
final List<Property> properties = response.getProperties();
|
||||
public static BrowserFile getModelFromResponse(Response response, String remotePath) {
|
||||
BrowserFile browserFile = new BrowserFile();
|
||||
browserFile.setPath(Uri.decode(remotePath));
|
||||
browserFile.setDisplayName(Uri.decode(new File(remotePath).getName()));
|
||||
final List<Property> properties = response.getProperties();
|
||||
|
||||
for (Property property : properties) {
|
||||
if (property instanceof OCId) {
|
||||
browserFile.setRemoteId(((OCId) property).getOcId());
|
||||
}
|
||||
for (Property property : properties) {
|
||||
if (property instanceof OCId) {
|
||||
browserFile.setRemoteId(((OCId) property).getOcId());
|
||||
}
|
||||
|
||||
if (property instanceof ResourceType) {
|
||||
browserFile.isFile =
|
||||
!(((ResourceType) property).getTypes().contains(ResourceType.Companion.getCOLLECTION()));
|
||||
}
|
||||
if (property instanceof ResourceType) {
|
||||
browserFile.isFile =
|
||||
!(((ResourceType) property).getTypes()
|
||||
.contains(ResourceType.Companion.getCOLLECTION()));
|
||||
}
|
||||
|
||||
if (property instanceof GetLastModified) {
|
||||
browserFile.setModifiedTimestamp(((GetLastModified) property).getLastModified());
|
||||
}
|
||||
if (property instanceof GetLastModified) {
|
||||
browserFile.setModifiedTimestamp(((GetLastModified) property).getLastModified());
|
||||
}
|
||||
|
||||
if (property instanceof GetContentType) {
|
||||
browserFile.setMimeType(((GetContentType) property).getType());
|
||||
}
|
||||
if (property instanceof GetContentType) {
|
||||
browserFile.setMimeType(((GetContentType) property).getType());
|
||||
}
|
||||
|
||||
if (property instanceof OCSize) {
|
||||
browserFile.setSize(((OCSize) property).getOcSize());
|
||||
}
|
||||
if (property instanceof OCSize) {
|
||||
browserFile.setSize(((OCSize) property).getOcSize());
|
||||
}
|
||||
|
||||
if (property instanceof NCPreview) {
|
||||
browserFile.setHasPreview(((NCPreview) property).isNcPreview());
|
||||
}
|
||||
if (property instanceof NCPreview) {
|
||||
browserFile.setHasPreview(((NCPreview) property).isNcPreview());
|
||||
}
|
||||
|
||||
if (property instanceof OCFavorite) {
|
||||
browserFile.setFavorite(((OCFavorite) property).isOcFavorite());
|
||||
}
|
||||
if (property instanceof OCFavorite) {
|
||||
browserFile.setFavorite(((OCFavorite) property).isOcFavorite());
|
||||
}
|
||||
|
||||
if (property instanceof DisplayName) {
|
||||
browserFile.setDisplayName(((DisplayName) property).getDisplayName());
|
||||
}
|
||||
if (property instanceof DisplayName) {
|
||||
browserFile.setDisplayName(((DisplayName) property).getDisplayName());
|
||||
}
|
||||
|
||||
if (property instanceof NCEncrypted) {
|
||||
browserFile.setEncrypted(((NCEncrypted) property).isNcEncrypted());
|
||||
}
|
||||
}
|
||||
|
||||
if (TextUtils.isEmpty(browserFile.getMimeType()) && !browserFile.isFile()) {
|
||||
browserFile.setMimeType("inode/directory");
|
||||
}
|
||||
|
||||
return browserFile;
|
||||
if (property instanceof NCEncrypted) {
|
||||
browserFile.setEncrypted(((NCEncrypted) property).isNcEncrypted());
|
||||
}
|
||||
}
|
||||
|
||||
if (TextUtils.isEmpty(browserFile.getMimeType()) && !browserFile.isFile()) {
|
||||
browserFile.setMimeType("inode/directory");
|
||||
}
|
||||
|
||||
return browserFile;
|
||||
}
|
||||
}
|
||||
|
@ -25,6 +25,6 @@ import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class DavResponse {
|
||||
Response response;
|
||||
Object data;
|
||||
Response response;
|
||||
Object data;
|
||||
}
|
||||
|
@ -34,39 +34,40 @@ import org.xmlpull.v1.XmlPullParser;
|
||||
import org.xmlpull.v1.XmlPullParserException;
|
||||
|
||||
public class NCEncrypted implements Property {
|
||||
public static final Name NAME = new Name(DavUtils.NC_NAMESPACE, DavUtils.EXTENDED_PROPERTY_IS_ENCRYPTED);
|
||||
public static final Name NAME =
|
||||
new Name(DavUtils.NC_NAMESPACE, DavUtils.EXTENDED_PROPERTY_IS_ENCRYPTED);
|
||||
|
||||
@Getter
|
||||
@Setter
|
||||
private boolean ncEncrypted;
|
||||
@Getter
|
||||
@Setter
|
||||
private boolean ncEncrypted;
|
||||
|
||||
private NCEncrypted(boolean isEncrypted) {
|
||||
ncEncrypted = isEncrypted;
|
||||
private NCEncrypted(boolean isEncrypted) {
|
||||
ncEncrypted = isEncrypted;
|
||||
}
|
||||
|
||||
public static class Factory implements PropertyFactory {
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Property create(@NotNull XmlPullParser xmlPullParser) {
|
||||
try {
|
||||
String text = XmlUtils.INSTANCE.readText(xmlPullParser);
|
||||
if (!TextUtils.isEmpty(text)) {
|
||||
return new NCEncrypted(Boolean.parseBoolean(text));
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (XmlPullParserException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return new NCEncrypted(false);
|
||||
}
|
||||
|
||||
public static class Factory implements PropertyFactory {
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Property create(@NotNull XmlPullParser xmlPullParser) {
|
||||
try {
|
||||
String text = XmlUtils.INSTANCE.readText(xmlPullParser);
|
||||
if (!TextUtils.isEmpty(text)) {
|
||||
return new NCEncrypted(Boolean.parseBoolean(text));
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (XmlPullParserException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return new NCEncrypted(false);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Name getName() {
|
||||
return NAME;
|
||||
}
|
||||
@NotNull
|
||||
@Override
|
||||
public Name getName() {
|
||||
return NAME;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -34,39 +34,40 @@ import org.xmlpull.v1.XmlPullParser;
|
||||
import org.xmlpull.v1.XmlPullParserException;
|
||||
|
||||
public class NCPreview implements Property {
|
||||
public static final Property.Name NAME = new Property.Name(DavUtils.NC_NAMESPACE, DavUtils.EXTENDED_PROPERTY_HAS_PREVIEW);
|
||||
public static final Property.Name NAME =
|
||||
new Property.Name(DavUtils.NC_NAMESPACE, DavUtils.EXTENDED_PROPERTY_HAS_PREVIEW);
|
||||
|
||||
@Getter
|
||||
@Setter
|
||||
private boolean ncPreview;
|
||||
@Getter
|
||||
@Setter
|
||||
private boolean ncPreview;
|
||||
|
||||
private NCPreview(boolean hasPreview) {
|
||||
ncPreview = hasPreview;
|
||||
private NCPreview(boolean hasPreview) {
|
||||
ncPreview = hasPreview;
|
||||
}
|
||||
|
||||
public static class Factory implements PropertyFactory {
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Property create(@NotNull XmlPullParser xmlPullParser) {
|
||||
try {
|
||||
String text = XmlUtils.INSTANCE.readText(xmlPullParser);
|
||||
if (!TextUtils.isEmpty(text)) {
|
||||
return new NCPreview(Boolean.parseBoolean(text));
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (XmlPullParserException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return new OCFavorite(false);
|
||||
}
|
||||
|
||||
public static class Factory implements PropertyFactory {
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Property create(@NotNull XmlPullParser xmlPullParser) {
|
||||
try {
|
||||
String text = XmlUtils.INSTANCE.readText(xmlPullParser);
|
||||
if (!TextUtils.isEmpty(text)) {
|
||||
return new NCPreview(Boolean.parseBoolean(text));
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (XmlPullParserException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return new OCFavorite(false);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Property.Name getName() {
|
||||
return NAME;
|
||||
}
|
||||
@NotNull
|
||||
@Override
|
||||
public Property.Name getName() {
|
||||
return NAME;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -34,39 +34,40 @@ import org.xmlpull.v1.XmlPullParser;
|
||||
import org.xmlpull.v1.XmlPullParserException;
|
||||
|
||||
public class OCFavorite implements Property {
|
||||
public static final Property.Name NAME = new Property.Name(DavUtils.OC_NAMESPACE, DavUtils.EXTENDED_PROPERTY_FAVORITE);
|
||||
public static final Property.Name NAME =
|
||||
new Property.Name(DavUtils.OC_NAMESPACE, DavUtils.EXTENDED_PROPERTY_FAVORITE);
|
||||
|
||||
@Getter
|
||||
@Setter
|
||||
private boolean ocFavorite;
|
||||
@Getter
|
||||
@Setter
|
||||
private boolean ocFavorite;
|
||||
|
||||
OCFavorite(boolean isFavorite) {
|
||||
ocFavorite = isFavorite;
|
||||
OCFavorite(boolean isFavorite) {
|
||||
ocFavorite = isFavorite;
|
||||
}
|
||||
|
||||
public static class Factory implements PropertyFactory {
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Property create(@NotNull XmlPullParser xmlPullParser) {
|
||||
try {
|
||||
String text = XmlUtils.INSTANCE.readText(xmlPullParser);
|
||||
if (!TextUtils.isEmpty(text)) {
|
||||
return new OCFavorite(Boolean.parseBoolean(text));
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (XmlPullParserException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return new OCFavorite(false);
|
||||
}
|
||||
|
||||
public static class Factory implements PropertyFactory {
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Property create(@NotNull XmlPullParser xmlPullParser) {
|
||||
try {
|
||||
String text = XmlUtils.INSTANCE.readText(xmlPullParser);
|
||||
if (!TextUtils.isEmpty(text)) {
|
||||
return new OCFavorite(Boolean.parseBoolean(text));
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (XmlPullParserException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return new OCFavorite(false);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Property.Name getName() {
|
||||
return NAME;
|
||||
}
|
||||
@NotNull
|
||||
@Override
|
||||
public Property.Name getName() {
|
||||
return NAME;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -34,39 +34,40 @@ import org.xmlpull.v1.XmlPullParser;
|
||||
import org.xmlpull.v1.XmlPullParserException;
|
||||
|
||||
public class OCId implements Property {
|
||||
public static final Name NAME = new Name(DavUtils.OC_NAMESPACE, DavUtils.EXTENDED_PROPERTY_NAME_REMOTE_ID);
|
||||
public static final Name NAME =
|
||||
new Name(DavUtils.OC_NAMESPACE, DavUtils.EXTENDED_PROPERTY_NAME_REMOTE_ID);
|
||||
|
||||
@Getter
|
||||
@Setter
|
||||
private String ocId;
|
||||
@Getter
|
||||
@Setter
|
||||
private String ocId;
|
||||
|
||||
private OCId(String id) {
|
||||
ocId = id;
|
||||
private OCId(String id) {
|
||||
ocId = id;
|
||||
}
|
||||
|
||||
public static class Factory implements PropertyFactory {
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Property create(@NotNull XmlPullParser xmlPullParser) {
|
||||
try {
|
||||
String text = XmlUtils.INSTANCE.readText(xmlPullParser);
|
||||
if (!TextUtils.isEmpty(text)) {
|
||||
return new OCId(text);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (XmlPullParserException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return new OCId("");
|
||||
}
|
||||
|
||||
public static class Factory implements PropertyFactory {
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Property create(@NotNull XmlPullParser xmlPullParser) {
|
||||
try {
|
||||
String text = XmlUtils.INSTANCE.readText(xmlPullParser);
|
||||
if (!TextUtils.isEmpty(text)) {
|
||||
return new OCId(text);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (XmlPullParserException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return new OCId("");
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Name getName() {
|
||||
return NAME;
|
||||
}
|
||||
@NotNull
|
||||
@Override
|
||||
public Name getName() {
|
||||
return NAME;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -34,39 +34,40 @@ import org.xmlpull.v1.XmlPullParser;
|
||||
import org.xmlpull.v1.XmlPullParserException;
|
||||
|
||||
public class OCSize implements Property {
|
||||
public static final Property.Name NAME = new Property.Name(DavUtils.OC_NAMESPACE, DavUtils.EXTENDED_PROPERTY_NAME_SIZE);
|
||||
public static final Property.Name NAME =
|
||||
new Property.Name(DavUtils.OC_NAMESPACE, DavUtils.EXTENDED_PROPERTY_NAME_SIZE);
|
||||
|
||||
@Getter
|
||||
@Setter
|
||||
private long ocSize;
|
||||
@Getter
|
||||
@Setter
|
||||
private long ocSize;
|
||||
|
||||
private OCSize(long size) {
|
||||
ocSize = size;
|
||||
private OCSize(long size) {
|
||||
ocSize = size;
|
||||
}
|
||||
|
||||
public static class Factory implements PropertyFactory {
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Property create(@NotNull XmlPullParser xmlPullParser) {
|
||||
try {
|
||||
String text = XmlUtils.INSTANCE.readText(xmlPullParser);
|
||||
if (!TextUtils.isEmpty(text)) {
|
||||
return new OCSize(Long.parseLong(text));
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (XmlPullParserException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return new OCSize(-1);
|
||||
}
|
||||
|
||||
public static class Factory implements PropertyFactory {
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Property create(@NotNull XmlPullParser xmlPullParser) {
|
||||
try {
|
||||
String text = XmlUtils.INSTANCE.readText(xmlPullParser);
|
||||
if (!TextUtils.isEmpty(text)) {
|
||||
return new OCSize(Long.parseLong(text));
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (XmlPullParserException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return new OCSize(-1);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Name getName() {
|
||||
return NAME;
|
||||
}
|
||||
@NotNull
|
||||
@Override
|
||||
public Name getName() {
|
||||
return NAME;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -33,36 +33,36 @@ import java.util.concurrent.Callable;
|
||||
import okhttp3.OkHttpClient;
|
||||
|
||||
public class DavListing extends ListingAbstractClass {
|
||||
private DavResponse davResponse = new DavResponse();
|
||||
private DavResponse davResponse = new DavResponse();
|
||||
|
||||
public DavListing(ListingInterface listingInterface) {
|
||||
super(listingInterface);
|
||||
}
|
||||
public DavListing(ListingInterface listingInterface) {
|
||||
super(listingInterface);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void getFiles(String path, UserEntity currentUser, @Nullable OkHttpClient okHttpClient) {
|
||||
Single.fromCallable(new Callable<ReadFilesystemOperation>() {
|
||||
@Override
|
||||
public ReadFilesystemOperation call() {
|
||||
return new ReadFilesystemOperation(okHttpClient, currentUser, path, 1);
|
||||
}
|
||||
}).subscribeOn(Schedulers.io())
|
||||
.subscribe(new SingleObserver<ReadFilesystemOperation>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
@Override
|
||||
public void getFiles(String path, UserEntity currentUser, @Nullable OkHttpClient okHttpClient) {
|
||||
Single.fromCallable(new Callable<ReadFilesystemOperation>() {
|
||||
@Override
|
||||
public ReadFilesystemOperation call() {
|
||||
return new ReadFilesystemOperation(okHttpClient, currentUser, path, 1);
|
||||
}
|
||||
}).subscribeOn(Schedulers.io())
|
||||
.subscribe(new SingleObserver<ReadFilesystemOperation>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onSuccess(ReadFilesystemOperation readFilesystemOperation) {
|
||||
davResponse = readFilesystemOperation.readRemotePath();
|
||||
listingInterface.listingResult(davResponse);
|
||||
}
|
||||
@Override
|
||||
public void onSuccess(ReadFilesystemOperation readFilesystemOperation) {
|
||||
davResponse = readFilesystemOperation.readRemotePath();
|
||||
listingInterface.listingResult(davResponse);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
listingInterface.listingResult(davResponse);
|
||||
}
|
||||
});
|
||||
}
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
listingInterface.listingResult(davResponse);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -27,22 +27,23 @@ import com.nextcloud.talk.models.database.UserEntity;
|
||||
import okhttp3.OkHttpClient;
|
||||
|
||||
public abstract class ListingAbstractClass {
|
||||
Handler handler;
|
||||
ListingInterface listingInterface;
|
||||
Handler handler;
|
||||
ListingInterface listingInterface;
|
||||
|
||||
ListingAbstractClass(ListingInterface listingInterface) {
|
||||
handler = new Handler();
|
||||
this.listingInterface = listingInterface;
|
||||
}
|
||||
ListingAbstractClass(ListingInterface listingInterface) {
|
||||
handler = new Handler();
|
||||
this.listingInterface = listingInterface;
|
||||
}
|
||||
|
||||
public abstract void getFiles(String path, UserEntity currentUser, @Nullable OkHttpClient okHttpClient);
|
||||
public abstract void getFiles(String path, UserEntity currentUser,
|
||||
@Nullable OkHttpClient okHttpClient);
|
||||
|
||||
public void cancelAllJobs() {
|
||||
handler.removeCallbacksAndMessages(null);
|
||||
}
|
||||
public void cancelAllJobs() {
|
||||
handler.removeCallbacksAndMessages(null);
|
||||
}
|
||||
|
||||
public void tearDown() {
|
||||
cancelAllJobs();
|
||||
handler = null;
|
||||
}
|
||||
public void tearDown() {
|
||||
cancelAllJobs();
|
||||
handler = null;
|
||||
}
|
||||
}
|
||||
|
@ -42,78 +42,76 @@ import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
public class DavUtils {
|
||||
public static final String OC_NAMESPACE = "http://owncloud.org/ns";
|
||||
public static final String NC_NAMESPACE = "http://nextcloud.org/ns";
|
||||
public static final String DAV_PATH = "/remote.php/dav/files/";
|
||||
public static final String OC_NAMESPACE = "http://owncloud.org/ns";
|
||||
public static final String NC_NAMESPACE = "http://nextcloud.org/ns";
|
||||
public static final String DAV_PATH = "/remote.php/dav/files/";
|
||||
|
||||
public static final String EXTENDED_PROPERTY_NAME_PERMISSIONS = "permissions";
|
||||
public static final String EXTENDED_PROPERTY_NAME_REMOTE_ID = "id";
|
||||
public static final String EXTENDED_PROPERTY_NAME_SIZE = "size";
|
||||
public static final String EXTENDED_PROPERTY_FAVORITE = "favorite";
|
||||
public static final String EXTENDED_PROPERTY_IS_ENCRYPTED = "is-encrypted";
|
||||
public static final String EXTENDED_PROPERTY_MOUNT_TYPE = "mount-type";
|
||||
public static final String EXTENDED_PROPERTY_OWNER_ID = "owner-id";
|
||||
public static final String EXTENDED_PROPERTY_OWNER_DISPLAY_NAME = "owner-display-name";
|
||||
public static final String EXTENDED_PROPERTY_UNREAD_COMMENTS = "comments-unread";
|
||||
public static final String EXTENDED_PROPERTY_HAS_PREVIEW = "has-preview";
|
||||
public static final String EXTENDED_PROPERTY_NOTE = "note";
|
||||
public static final String TRASHBIN_FILENAME = "trashbin-filename";
|
||||
public static final String TRASHBIN_ORIGINAL_LOCATION = "trashbin-original-location";
|
||||
public static final String TRASHBIN_DELETION_TIME = "trashbin-deletion-time";
|
||||
public static final String EXTENDED_PROPERTY_NAME_PERMISSIONS = "permissions";
|
||||
public static final String EXTENDED_PROPERTY_NAME_REMOTE_ID = "id";
|
||||
public static final String EXTENDED_PROPERTY_NAME_SIZE = "size";
|
||||
public static final String EXTENDED_PROPERTY_FAVORITE = "favorite";
|
||||
public static final String EXTENDED_PROPERTY_IS_ENCRYPTED = "is-encrypted";
|
||||
public static final String EXTENDED_PROPERTY_MOUNT_TYPE = "mount-type";
|
||||
public static final String EXTENDED_PROPERTY_OWNER_ID = "owner-id";
|
||||
public static final String EXTENDED_PROPERTY_OWNER_DISPLAY_NAME = "owner-display-name";
|
||||
public static final String EXTENDED_PROPERTY_UNREAD_COMMENTS = "comments-unread";
|
||||
public static final String EXTENDED_PROPERTY_HAS_PREVIEW = "has-preview";
|
||||
public static final String EXTENDED_PROPERTY_NOTE = "note";
|
||||
public static final String TRASHBIN_FILENAME = "trashbin-filename";
|
||||
public static final String TRASHBIN_ORIGINAL_LOCATION = "trashbin-original-location";
|
||||
public static final String TRASHBIN_DELETION_TIME = "trashbin-deletion-time";
|
||||
|
||||
public static final String PROPERTY_QUOTA_USED_BYTES = "quota-used-bytes";
|
||||
public static final String PROPERTY_QUOTA_AVAILABLE_BYTES = "quota-available-bytes";
|
||||
public static final String PROPERTY_QUOTA_USED_BYTES = "quota-used-bytes";
|
||||
public static final String PROPERTY_QUOTA_AVAILABLE_BYTES = "quota-available-bytes";
|
||||
|
||||
static Property.Name[] getAllPropSet() {
|
||||
List<Property.Name> propSet = new ArrayList<>();
|
||||
static Property.Name[] getAllPropSet() {
|
||||
List<Property.Name> propSet = new ArrayList<>();
|
||||
|
||||
propSet.add(DisplayName.NAME);
|
||||
propSet.add(GetContentType.NAME);
|
||||
propSet.add(GetContentLength.NAME);
|
||||
propSet.add(GetContentType.NAME);
|
||||
propSet.add(GetContentLength.NAME);
|
||||
propSet.add(GetLastModified.NAME);
|
||||
propSet.add(CreationDate.NAME);
|
||||
propSet.add(GetETag.NAME);
|
||||
propSet.add(ResourceType.NAME);
|
||||
propSet.add(DisplayName.NAME);
|
||||
propSet.add(GetContentType.NAME);
|
||||
propSet.add(GetContentLength.NAME);
|
||||
propSet.add(GetContentType.NAME);
|
||||
propSet.add(GetContentLength.NAME);
|
||||
propSet.add(GetLastModified.NAME);
|
||||
propSet.add(CreationDate.NAME);
|
||||
propSet.add(GetETag.NAME);
|
||||
propSet.add(ResourceType.NAME);
|
||||
|
||||
propSet.add(new Property.Name(OC_NAMESPACE, EXTENDED_PROPERTY_NAME_PERMISSIONS));
|
||||
propSet.add(OCId.NAME);
|
||||
propSet.add(OCSize.NAME);
|
||||
propSet.add(OCFavorite.NAME);
|
||||
propSet.add(new Property.Name(OC_NAMESPACE, EXTENDED_PROPERTY_OWNER_ID));
|
||||
propSet.add(new Property.Name(OC_NAMESPACE, EXTENDED_PROPERTY_OWNER_DISPLAY_NAME));
|
||||
propSet.add(new Property.Name(OC_NAMESPACE, EXTENDED_PROPERTY_UNREAD_COMMENTS));
|
||||
propSet.add(new Property.Name(OC_NAMESPACE, EXTENDED_PROPERTY_NAME_PERMISSIONS));
|
||||
propSet.add(OCId.NAME);
|
||||
propSet.add(OCSize.NAME);
|
||||
propSet.add(OCFavorite.NAME);
|
||||
propSet.add(new Property.Name(OC_NAMESPACE, EXTENDED_PROPERTY_OWNER_ID));
|
||||
propSet.add(new Property.Name(OC_NAMESPACE, EXTENDED_PROPERTY_OWNER_DISPLAY_NAME));
|
||||
propSet.add(new Property.Name(OC_NAMESPACE, EXTENDED_PROPERTY_UNREAD_COMMENTS));
|
||||
|
||||
propSet.add(NCEncrypted.NAME);
|
||||
propSet.add(new Property.Name(NC_NAMESPACE, EXTENDED_PROPERTY_MOUNT_TYPE));
|
||||
propSet.add(NCPreview.NAME);
|
||||
propSet.add(new Property.Name(NC_NAMESPACE, EXTENDED_PROPERTY_NOTE));
|
||||
propSet.add(NCEncrypted.NAME);
|
||||
propSet.add(new Property.Name(NC_NAMESPACE, EXTENDED_PROPERTY_MOUNT_TYPE));
|
||||
propSet.add(NCPreview.NAME);
|
||||
propSet.add(new Property.Name(NC_NAMESPACE, EXTENDED_PROPERTY_NOTE));
|
||||
|
||||
return propSet.toArray(new Property.Name[0]);
|
||||
return propSet.toArray(new Property.Name[0]);
|
||||
}
|
||||
|
||||
public static void registerCustomFactories() {
|
||||
PropertyRegistry propertyRegistry = PropertyRegistry.INSTANCE;
|
||||
try {
|
||||
Field factories = propertyRegistry.getClass().getDeclaredField("factories");
|
||||
factories.setAccessible(true);
|
||||
Map<Property.Name, PropertyFactory> reflectionMap = (HashMap<Property.Name,
|
||||
PropertyFactory>) factories.get(propertyRegistry);
|
||||
|
||||
reflectionMap.put(OCId.NAME, new OCId.Factory());
|
||||
reflectionMap.put(NCPreview.NAME, new NCPreview.Factory());
|
||||
reflectionMap.put(NCEncrypted.NAME, new NCEncrypted.Factory());
|
||||
reflectionMap.put(OCFavorite.NAME, new OCFavorite.Factory());
|
||||
reflectionMap.put(OCSize.NAME, new OCSize.Factory());
|
||||
|
||||
factories.set(propertyRegistry, reflectionMap);
|
||||
} catch (NoSuchFieldException e) {
|
||||
e.printStackTrace();
|
||||
} catch (IllegalAccessException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
public static void registerCustomFactories() {
|
||||
PropertyRegistry propertyRegistry = PropertyRegistry.INSTANCE;
|
||||
try {
|
||||
Field factories = propertyRegistry.getClass().getDeclaredField("factories");
|
||||
factories.setAccessible(true);
|
||||
Map<Property.Name, PropertyFactory> reflectionMap = (HashMap<Property.Name,
|
||||
PropertyFactory>) factories.get(propertyRegistry);
|
||||
|
||||
reflectionMap.put(OCId.NAME, new OCId.Factory());
|
||||
reflectionMap.put(NCPreview.NAME, new NCPreview.Factory());
|
||||
reflectionMap.put(NCEncrypted.NAME, new NCEncrypted.Factory());
|
||||
reflectionMap.put(OCFavorite.NAME, new OCFavorite.Factory());
|
||||
reflectionMap.put(OCSize.NAME, new OCSize.Factory());
|
||||
|
||||
factories.set(propertyRegistry, reflectionMap);
|
||||
} catch (NoSuchFieldException e) {
|
||||
e.printStackTrace();
|
||||
} catch (IllegalAccessException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -37,63 +37,64 @@ import okhttp3.HttpUrl;
|
||||
import okhttp3.OkHttpClient;
|
||||
|
||||
public class ReadFilesystemOperation {
|
||||
private final OkHttpClient okHttpClient;
|
||||
private final String url;
|
||||
private final int depth;
|
||||
private final String basePath;
|
||||
private final OkHttpClient okHttpClient;
|
||||
private final String url;
|
||||
private final int depth;
|
||||
private final String basePath;
|
||||
|
||||
public ReadFilesystemOperation(OkHttpClient okHttpClient, UserEntity currentUser, String path, int depth) {
|
||||
OkHttpClient.Builder okHttpClientBuilder = okHttpClient.newBuilder();
|
||||
okHttpClientBuilder.followRedirects(false);
|
||||
okHttpClientBuilder.followSslRedirects(false);
|
||||
okHttpClientBuilder.authenticator(new RestModule.MagicAuthenticator(ApiUtils.getCredentials(currentUser.getUsername(), currentUser.getToken()), "Authorization"));
|
||||
this.okHttpClient = okHttpClientBuilder.build();
|
||||
this.basePath = currentUser.getBaseUrl() + DavUtils.DAV_PATH + currentUser.getUserId();
|
||||
this.url = basePath + path;
|
||||
this.depth = depth;
|
||||
public ReadFilesystemOperation(OkHttpClient okHttpClient, UserEntity currentUser, String path,
|
||||
int depth) {
|
||||
OkHttpClient.Builder okHttpClientBuilder = okHttpClient.newBuilder();
|
||||
okHttpClientBuilder.followRedirects(false);
|
||||
okHttpClientBuilder.followSslRedirects(false);
|
||||
okHttpClientBuilder.authenticator(new RestModule.MagicAuthenticator(
|
||||
ApiUtils.getCredentials(currentUser.getUsername(), currentUser.getToken()),
|
||||
"Authorization"));
|
||||
this.okHttpClient = okHttpClientBuilder.build();
|
||||
this.basePath = currentUser.getBaseUrl() + DavUtils.DAV_PATH + currentUser.getUserId();
|
||||
this.url = basePath + path;
|
||||
this.depth = depth;
|
||||
}
|
||||
|
||||
public DavResponse readRemotePath() {
|
||||
DavResponse davResponse = new DavResponse();
|
||||
final List<Response> memberElements = new ArrayList<>();
|
||||
final Response[] rootElement = new Response[1];
|
||||
final List<BrowserFile> remoteFiles = new ArrayList<>();
|
||||
|
||||
try {
|
||||
new DavResource(okHttpClient, HttpUrl.parse(url)).propfind(depth, DavUtils.getAllPropSet(),
|
||||
new Function2<Response, Response.HrefRelation, Unit>() {
|
||||
@Override
|
||||
public Unit invoke(Response response, Response.HrefRelation hrefRelation) {
|
||||
davResponse.setResponse(response);
|
||||
switch (hrefRelation) {
|
||||
case MEMBER:
|
||||
memberElements.add(response);
|
||||
break;
|
||||
case SELF:
|
||||
rootElement[0] = response;
|
||||
break;
|
||||
case OTHER:
|
||||
default:
|
||||
}
|
||||
return Unit.INSTANCE;
|
||||
}
|
||||
});
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (DavException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
public DavResponse readRemotePath() {
|
||||
DavResponse davResponse = new DavResponse();
|
||||
final List<Response> memberElements = new ArrayList<>();
|
||||
final Response[] rootElement = new Response[1];
|
||||
final List<BrowserFile> remoteFiles = new ArrayList<>();
|
||||
|
||||
try {
|
||||
new DavResource(okHttpClient, HttpUrl.parse(url)).propfind(depth, DavUtils.getAllPropSet(),
|
||||
new Function2<Response, Response.HrefRelation, Unit>() {
|
||||
@Override
|
||||
public Unit invoke(Response response, Response.HrefRelation hrefRelation) {
|
||||
davResponse.setResponse(response);
|
||||
switch (hrefRelation) {
|
||||
case MEMBER:
|
||||
memberElements.add(response);
|
||||
break;
|
||||
case SELF:
|
||||
rootElement[0] = response;
|
||||
break;
|
||||
case OTHER:
|
||||
default:
|
||||
}
|
||||
return Unit.INSTANCE;
|
||||
}
|
||||
});
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} catch (DavException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
|
||||
remoteFiles.add(BrowserFile.getModelFromResponse(rootElement[0],
|
||||
rootElement[0].getHref().toString().substring(basePath.length())));
|
||||
for (Response memberElement : memberElements) {
|
||||
remoteFiles.add(BrowserFile.getModelFromResponse(memberElement,
|
||||
memberElement.getHref().toString().substring(basePath.length())));
|
||||
}
|
||||
|
||||
davResponse.setData(remoteFiles);
|
||||
return davResponse;
|
||||
remoteFiles.add(BrowserFile.getModelFromResponse(rootElement[0],
|
||||
rootElement[0].getHref().toString().substring(basePath.length())));
|
||||
for (Response memberElement : memberElements) {
|
||||
remoteFiles.add(BrowserFile.getModelFromResponse(memberElement,
|
||||
memberElement.getHref().toString().substring(basePath.length())));
|
||||
}
|
||||
|
||||
davResponse.setData(remoteFiles);
|
||||
return davResponse;
|
||||
}
|
||||
}
|
||||
|
@ -36,9 +36,6 @@ import autodagger.AutoInjector;
|
||||
import butterknife.BindView;
|
||||
import com.bluelinelabs.conductor.RouterTransaction;
|
||||
import com.bluelinelabs.conductor.changehandler.HorizontalChangeHandler;
|
||||
import com.nextcloud.talk.models.json.conversations.RoomsOverall;
|
||||
import com.nextcloud.talk.models.json.generic.Status;
|
||||
import com.nextcloud.talk.models.json.userprofile.UserProfileOverall;
|
||||
import com.nextcloud.talk.R;
|
||||
import com.nextcloud.talk.api.NcApi;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
@ -48,6 +45,9 @@ import com.nextcloud.talk.jobs.CapabilitiesWorker;
|
||||
import com.nextcloud.talk.jobs.PushRegistrationWorker;
|
||||
import com.nextcloud.talk.jobs.SignalingSettingsWorker;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.models.json.conversations.RoomsOverall;
|
||||
import com.nextcloud.talk.models.json.generic.Status;
|
||||
import com.nextcloud.talk.models.json.userprofile.UserProfileOverall;
|
||||
import com.nextcloud.talk.newarch.features.conversationsList.ConversationsListView;
|
||||
import com.nextcloud.talk.utils.ApiUtils;
|
||||
import com.nextcloud.talk.utils.ClosedInterfaceImpl;
|
||||
@ -67,426 +67,435 @@ import org.greenrobot.eventbus.EventBus;
|
||||
import org.greenrobot.eventbus.Subscribe;
|
||||
import org.greenrobot.eventbus.ThreadMode;
|
||||
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class AccountVerificationController extends BaseController {
|
||||
|
||||
public static final String TAG = "AccountVerificationController";
|
||||
public static final String TAG = "AccountVerificationController";
|
||||
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
@Inject
|
||||
CookieManager cookieManager;
|
||||
@Inject
|
||||
CookieManager cookieManager;
|
||||
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
|
||||
@BindView(R.id.progress_text)
|
||||
TextView progressText;
|
||||
@BindView(R.id.progress_text)
|
||||
TextView progressText;
|
||||
|
||||
private long internalAccountId = -1;
|
||||
private long internalAccountId = -1;
|
||||
|
||||
private String baseUrl;
|
||||
private String username;
|
||||
private String token;
|
||||
private boolean isAccountImport;
|
||||
private String originalProtocol;
|
||||
private String baseUrl;
|
||||
private String username;
|
||||
private String token;
|
||||
private boolean isAccountImport;
|
||||
private String originalProtocol;
|
||||
|
||||
public AccountVerificationController(Bundle args) {
|
||||
super();
|
||||
if (args != null) {
|
||||
baseUrl = args.getString(BundleKeys.INSTANCE.getKEY_BASE_URL());
|
||||
username = args.getString(BundleKeys.INSTANCE.getKEY_USERNAME());
|
||||
token = args.getString(BundleKeys.INSTANCE.getKEY_TOKEN());
|
||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_IS_ACCOUNT_IMPORT())) {
|
||||
isAccountImport = true;
|
||||
}
|
||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_ORIGINAL_PROTOCOL())) {
|
||||
originalProtocol = args.getString(BundleKeys.INSTANCE.getKEY_ORIGINAL_PROTOCOL());
|
||||
}
|
||||
}
|
||||
public AccountVerificationController(Bundle args) {
|
||||
super();
|
||||
if (args != null) {
|
||||
baseUrl = args.getString(BundleKeys.INSTANCE.getKEY_BASE_URL());
|
||||
username = args.getString(BundleKeys.INSTANCE.getKEY_USERNAME());
|
||||
token = args.getString(BundleKeys.INSTANCE.getKEY_TOKEN());
|
||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_IS_ACCOUNT_IMPORT())) {
|
||||
isAccountImport = true;
|
||||
}
|
||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_ORIGINAL_PROTOCOL())) {
|
||||
originalProtocol = args.getString(BundleKeys.INSTANCE.getKEY_ORIGINAL_PROTOCOL());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_account_verification, container, false);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDetach(@NonNull View view) {
|
||||
eventBus.unregister(this);
|
||||
super.onDetach(view);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
eventBus.register(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_account_verification, container, false);
|
||||
if (getActionBar() != null) {
|
||||
getActionBar().hide();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDetach(@NonNull View view) {
|
||||
eventBus.unregister(this);
|
||||
super.onDetach(view);
|
||||
if (isAccountImport && !baseUrl.startsWith("http://") && !baseUrl.startsWith("https://")
|
||||
|| (!TextUtils
|
||||
.isEmpty(originalProtocol) && !baseUrl.startsWith(originalProtocol))) {
|
||||
determineBaseUrlProtocol(true);
|
||||
} else {
|
||||
checkEverything();
|
||||
}
|
||||
}
|
||||
|
||||
private void checkEverything() {
|
||||
String credentials = ApiUtils.getCredentials(username, token);
|
||||
cookieManager.getCookieStore().removeAll();
|
||||
|
||||
findServerTalkApp(credentials);
|
||||
}
|
||||
|
||||
private void determineBaseUrlProtocol(boolean checkForcedHttps) {
|
||||
cookieManager.getCookieStore().removeAll();
|
||||
|
||||
String queryUrl;
|
||||
|
||||
baseUrl = baseUrl.replace("http://", "").replace("https://", "");
|
||||
|
||||
if (checkForcedHttps) {
|
||||
queryUrl = "https://" + baseUrl + ApiUtils.getUrlPostfixForStatus();
|
||||
} else {
|
||||
queryUrl = "http://" + baseUrl + ApiUtils.getUrlPostfixForStatus();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
eventBus.register(this);
|
||||
}
|
||||
ncApi.getServerStatus(queryUrl)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<Status>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
|
||||
}
|
||||
|
||||
if (getActionBar() != null) {
|
||||
getActionBar().hide();
|
||||
}
|
||||
|
||||
if (isAccountImport && !baseUrl.startsWith("http://") && !baseUrl.startsWith("https://") || (!TextUtils
|
||||
.isEmpty(originalProtocol) && !baseUrl.startsWith(originalProtocol))) {
|
||||
determineBaseUrlProtocol(true);
|
||||
} else {
|
||||
checkEverything();
|
||||
}
|
||||
}
|
||||
|
||||
private void checkEverything() {
|
||||
String credentials = ApiUtils.getCredentials(username, token);
|
||||
cookieManager.getCookieStore().removeAll();
|
||||
|
||||
findServerTalkApp(credentials);
|
||||
}
|
||||
|
||||
private void determineBaseUrlProtocol(boolean checkForcedHttps) {
|
||||
cookieManager.getCookieStore().removeAll();
|
||||
|
||||
String queryUrl;
|
||||
|
||||
baseUrl = baseUrl.replace("http://", "").replace("https://", "");
|
||||
|
||||
if (checkForcedHttps) {
|
||||
queryUrl = "https://" + baseUrl + ApiUtils.getUrlPostfixForStatus();
|
||||
} else {
|
||||
queryUrl = "http://" + baseUrl + ApiUtils.getUrlPostfixForStatus();
|
||||
}
|
||||
|
||||
ncApi.getServerStatus(queryUrl)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<Status>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(Status status) {
|
||||
if (checkForcedHttps) {
|
||||
baseUrl = "https://" + baseUrl;
|
||||
} else {
|
||||
baseUrl = "http://" + baseUrl;
|
||||
}
|
||||
|
||||
if (isAccountImport) {
|
||||
getRouter().replaceTopController(RouterTransaction.with(new WebViewLoginController(baseUrl,
|
||||
false, username, ""))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else {
|
||||
checkEverything();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
if (checkForcedHttps) {
|
||||
determineBaseUrlProtocol(false);
|
||||
} else {
|
||||
abortVerification();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void findServerTalkApp(String credentials) {
|
||||
ncApi.getRooms(credentials, ApiUtils.getUrlForGetRooms(baseUrl))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<RoomsOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(RoomsOverall roomsOverall) {
|
||||
fetchProfile(credentials);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
if (getActivity() != null && getResources() != null) {
|
||||
getActivity().runOnUiThread(() -> progressText.setText(String.format(getResources().getString(
|
||||
R.string.nc_nextcloud_talk_app_not_installed), getResources().getString(R.string.nc_app_name))));
|
||||
}
|
||||
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(
|
||||
ApplicationWideMessageHolder.MessageType.SERVER_WITHOUT_TALK);
|
||||
|
||||
abortVerification();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void storeProfile(String displayName, String userId) {
|
||||
userUtils.createOrUpdateUser(username, token,
|
||||
baseUrl, displayName, null, true,
|
||||
userId, null, null,
|
||||
appPreferences.getTemporaryClientCertAlias(), null)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<UserEntity>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(UserEntity userEntity) {
|
||||
internalAccountId = userEntity.getId();
|
||||
|
||||
if (new ClosedInterfaceImpl().isGooglePlayServicesAvailable()) {
|
||||
registerForPush();
|
||||
} else {
|
||||
getActivity().runOnUiThread(() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_push_disabled)));
|
||||
fetchAndStoreCapabilities();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
progressText.setText(progressText.getText().toString() +
|
||||
"\n" +
|
||||
getResources().getString(
|
||||
R.string.nc_display_name_not_stored));
|
||||
abortVerification();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void fetchProfile(String credentials) {
|
||||
ncApi.getUserProfile(credentials,
|
||||
ApiUtils.getUrlForUserProfile(baseUrl))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<UserProfileOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(UserProfileOverall userProfileOverall) {
|
||||
String displayName = null;
|
||||
if (!TextUtils.isEmpty(userProfileOverall.getOcs().getData()
|
||||
.getDisplayName())) {
|
||||
displayName = userProfileOverall.getOcs().getData()
|
||||
.getDisplayName();
|
||||
} else if (!TextUtils.isEmpty(userProfileOverall.getOcs().getData()
|
||||
.getDisplayNameAlt())) {
|
||||
displayName = userProfileOverall.getOcs().getData()
|
||||
.getDisplayNameAlt();
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(displayName)) {
|
||||
storeProfile(displayName, userProfileOverall.getOcs().getData().getUserId());
|
||||
} else {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_display_name_not_fetched)));
|
||||
}
|
||||
abortVerification();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_display_name_not_fetched)));
|
||||
}
|
||||
abortVerification();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void registerForPush() {
|
||||
OneTimeWorkRequest pushRegistrationWork = new OneTimeWorkRequest.Builder(PushRegistrationWorker.class).build();
|
||||
WorkManager.getInstance().enqueue(pushRegistrationWork);
|
||||
}
|
||||
|
||||
@Subscribe(threadMode = ThreadMode.BACKGROUND)
|
||||
public void onMessageEvent(EventStatus eventStatus) {
|
||||
if (eventStatus.getEventType().equals(EventStatus.EventType.PUSH_REGISTRATION)) {
|
||||
if (internalAccountId == eventStatus.getUserId() && !eventStatus.isAllGood() && getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_push_disabled)));
|
||||
}
|
||||
fetchAndStoreCapabilities();
|
||||
} else if (eventStatus.getEventType().equals(EventStatus.EventType.CAPABILITIES_FETCH)) {
|
||||
if (internalAccountId == eventStatus.getUserId() && !eventStatus.isAllGood()) {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_capabilities_failed)));
|
||||
}
|
||||
abortVerification();
|
||||
} else if (internalAccountId == eventStatus.getUserId() && eventStatus.isAllGood()) {
|
||||
fetchAndStoreExternalSignalingSettings();
|
||||
}
|
||||
} else if (eventStatus.getEventType().equals(EventStatus.EventType.SIGNALING_SETTINGS)) {
|
||||
if (internalAccountId == eventStatus.getUserId() && !eventStatus.isAllGood()) {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_external_server_failed)));
|
||||
}
|
||||
}
|
||||
|
||||
proceedWithLogin();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void fetchAndStoreCapabilities() {
|
||||
Data userData = new Data.Builder()
|
||||
.putLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), internalAccountId)
|
||||
.build();
|
||||
|
||||
OneTimeWorkRequest pushNotificationWork = new OneTimeWorkRequest.Builder(CapabilitiesWorker.class)
|
||||
.setInputData(userData)
|
||||
.build();
|
||||
WorkManager.getInstance().enqueue(pushNotificationWork);
|
||||
}
|
||||
|
||||
private void fetchAndStoreExternalSignalingSettings() {
|
||||
Data userData = new Data.Builder()
|
||||
.putLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), internalAccountId)
|
||||
.build();
|
||||
|
||||
OneTimeWorkRequest signalingSettings = new OneTimeWorkRequest.Builder(SignalingSettingsWorker.class)
|
||||
.setInputData(userData)
|
||||
.build();
|
||||
WorkManager.getInstance().enqueue(signalingSettings);
|
||||
}
|
||||
|
||||
private void proceedWithLogin() {
|
||||
cookieManager.getCookieStore().removeAll();
|
||||
userUtils.disableAllUsersWithoutId(internalAccountId);
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> {
|
||||
if (userUtils.getUsers().size() == 1) {
|
||||
getRouter().setRoot(RouterTransaction.with(new
|
||||
ConversationsListView())
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else {
|
||||
if (isAccountImport) {
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(
|
||||
ApplicationWideMessageHolder.MessageType.ACCOUNT_WAS_IMPORTED);
|
||||
}
|
||||
getRouter().popToRoot();
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
protected void onDestroyView(@NonNull View view) {
|
||||
super.onDestroyView(view);
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_FULL_SENSOR);
|
||||
}
|
||||
}
|
||||
|
||||
private void abortVerification() {
|
||||
|
||||
if (!isAccountImport) {
|
||||
if (internalAccountId != -1) {
|
||||
userUtils.deleteUserWithId(internalAccountId).subscribe(new CompletableObserver() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> {
|
||||
new Handler().postDelayed(() -> getRouter().popToRoot(), 7500);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
});
|
||||
@Override
|
||||
public void onNext(Status status) {
|
||||
if (checkForcedHttps) {
|
||||
baseUrl = "https://" + baseUrl;
|
||||
} else {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> {
|
||||
new Handler().postDelayed(() -> getRouter().popToRoot(), 7500);
|
||||
});
|
||||
}
|
||||
baseUrl = "http://" + baseUrl;
|
||||
}
|
||||
} else {
|
||||
|
||||
if (isAccountImport) {
|
||||
getRouter().replaceTopController(
|
||||
RouterTransaction.with(new WebViewLoginController(baseUrl,
|
||||
false, username, ""))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else {
|
||||
checkEverything();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
if (checkForcedHttps) {
|
||||
determineBaseUrlProtocol(false);
|
||||
} else {
|
||||
abortVerification();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void findServerTalkApp(String credentials) {
|
||||
ncApi.getRooms(credentials, ApiUtils.getUrlForGetRooms(baseUrl))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<RoomsOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(RoomsOverall roomsOverall) {
|
||||
fetchProfile(credentials);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
if (getActivity() != null && getResources() != null) {
|
||||
getActivity().runOnUiThread(
|
||||
() -> progressText.setText(String.format(getResources().getString(
|
||||
R.string.nc_nextcloud_talk_app_not_installed),
|
||||
getResources().getString(R.string.nc_app_name))));
|
||||
}
|
||||
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(
|
||||
ApplicationWideMessageHolder.MessageType.FAILED_TO_IMPORT_ACCOUNT);
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> new Handler().postDelayed(() -> {
|
||||
if (getRouter().hasRootController()) {
|
||||
if (getActivity() != null) {
|
||||
getRouter().popToRoot();
|
||||
}
|
||||
ApplicationWideMessageHolder.MessageType.SERVER_WITHOUT_TALK);
|
||||
|
||||
abortVerification();
|
||||
}
|
||||
|
||||
} else {
|
||||
if (userUtils.anyUserExists()) {
|
||||
getRouter().setRoot(RouterTransaction.with(new ConversationsListView())
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else {
|
||||
getRouter().setRoot(RouterTransaction.with(new ServerSelectionController())
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
}
|
||||
}
|
||||
}, 7500));
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void storeProfile(String displayName, String userId) {
|
||||
userUtils.createOrUpdateUser(username, token,
|
||||
baseUrl, displayName, null, true,
|
||||
userId, null, null,
|
||||
appPreferences.getTemporaryClientCertAlias(), null)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<UserEntity>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(UserEntity userEntity) {
|
||||
internalAccountId = userEntity.getId();
|
||||
|
||||
if (new ClosedInterfaceImpl().isGooglePlayServicesAvailable()) {
|
||||
registerForPush();
|
||||
} else {
|
||||
getActivity().runOnUiThread(
|
||||
() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_push_disabled)));
|
||||
fetchAndStoreCapabilities();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
progressText.setText(progressText.getText().toString() +
|
||||
"\n" +
|
||||
getResources().getString(
|
||||
R.string.nc_display_name_not_stored));
|
||||
abortVerification();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void fetchProfile(String credentials) {
|
||||
ncApi.getUserProfile(credentials,
|
||||
ApiUtils.getUrlForUserProfile(baseUrl))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<UserProfileOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(UserProfileOverall userProfileOverall) {
|
||||
String displayName = null;
|
||||
if (!TextUtils.isEmpty(userProfileOverall.getOcs().getData()
|
||||
.getDisplayName())) {
|
||||
displayName = userProfileOverall.getOcs().getData()
|
||||
.getDisplayName();
|
||||
} else if (!TextUtils.isEmpty(userProfileOverall.getOcs().getData()
|
||||
.getDisplayNameAlt())) {
|
||||
displayName = userProfileOverall.getOcs().getData()
|
||||
.getDisplayNameAlt();
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(displayName)) {
|
||||
storeProfile(displayName, userProfileOverall.getOcs().getData().getUserId());
|
||||
} else {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(
|
||||
() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_display_name_not_fetched)));
|
||||
}
|
||||
abortVerification();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(
|
||||
() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_display_name_not_fetched)));
|
||||
}
|
||||
abortVerification();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void registerForPush() {
|
||||
OneTimeWorkRequest pushRegistrationWork =
|
||||
new OneTimeWorkRequest.Builder(PushRegistrationWorker.class).build();
|
||||
WorkManager.getInstance().enqueue(pushRegistrationWork);
|
||||
}
|
||||
|
||||
@Subscribe(threadMode = ThreadMode.BACKGROUND)
|
||||
public void onMessageEvent(EventStatus eventStatus) {
|
||||
if (eventStatus.getEventType().equals(EventStatus.EventType.PUSH_REGISTRATION)) {
|
||||
if (internalAccountId == eventStatus.getUserId()
|
||||
&& !eventStatus.isAllGood()
|
||||
&& getActivity() != null) {
|
||||
getActivity().runOnUiThread(
|
||||
() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_push_disabled)));
|
||||
}
|
||||
fetchAndStoreCapabilities();
|
||||
} else if (eventStatus.getEventType().equals(EventStatus.EventType.CAPABILITIES_FETCH)) {
|
||||
if (internalAccountId == eventStatus.getUserId() && !eventStatus.isAllGood()) {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(
|
||||
() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_capabilities_failed)));
|
||||
}
|
||||
abortVerification();
|
||||
} else if (internalAccountId == eventStatus.getUserId() && eventStatus.isAllGood()) {
|
||||
fetchAndStoreExternalSignalingSettings();
|
||||
}
|
||||
} else if (eventStatus.getEventType().equals(EventStatus.EventType.SIGNALING_SETTINGS)) {
|
||||
if (internalAccountId == eventStatus.getUserId() && !eventStatus.isAllGood()) {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(
|
||||
() -> progressText.setText(progressText.getText().toString() + "\n" +
|
||||
getResources().getString(R.string.nc_external_server_failed)));
|
||||
}
|
||||
}
|
||||
|
||||
proceedWithLogin();
|
||||
}
|
||||
}
|
||||
|
||||
private void fetchAndStoreCapabilities() {
|
||||
Data userData = new Data.Builder()
|
||||
.putLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), internalAccountId)
|
||||
.build();
|
||||
|
||||
OneTimeWorkRequest pushNotificationWork =
|
||||
new OneTimeWorkRequest.Builder(CapabilitiesWorker.class)
|
||||
.setInputData(userData)
|
||||
.build();
|
||||
WorkManager.getInstance().enqueue(pushNotificationWork);
|
||||
}
|
||||
|
||||
private void fetchAndStoreExternalSignalingSettings() {
|
||||
Data userData = new Data.Builder()
|
||||
.putLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), internalAccountId)
|
||||
.build();
|
||||
|
||||
OneTimeWorkRequest signalingSettings =
|
||||
new OneTimeWorkRequest.Builder(SignalingSettingsWorker.class)
|
||||
.setInputData(userData)
|
||||
.build();
|
||||
WorkManager.getInstance().enqueue(signalingSettings);
|
||||
}
|
||||
|
||||
private void proceedWithLogin() {
|
||||
cookieManager.getCookieStore().removeAll();
|
||||
userUtils.disableAllUsersWithoutId(internalAccountId);
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> {
|
||||
if (userUtils.getUsers().size() == 1) {
|
||||
getRouter().setRoot(RouterTransaction.with(new
|
||||
ConversationsListView())
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else {
|
||||
if (isAccountImport) {
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(
|
||||
ApplicationWideMessageHolder.MessageType.ACCOUNT_WAS_IMPORTED);
|
||||
}
|
||||
getRouter().popToRoot();
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDestroyView(@NonNull View view) {
|
||||
super.onDestroyView(view);
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_FULL_SENSOR);
|
||||
}
|
||||
}
|
||||
|
||||
private void abortVerification() {
|
||||
|
||||
if (!isAccountImport) {
|
||||
if (internalAccountId != -1) {
|
||||
userUtils.deleteUserWithId(internalAccountId).subscribe(new CompletableObserver() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> {
|
||||
new Handler().postDelayed(() -> getRouter().popToRoot(), 7500);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
});
|
||||
} else {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> {
|
||||
new Handler().postDelayed(() -> getRouter().popToRoot(), 7500);
|
||||
});
|
||||
}
|
||||
}
|
||||
} else {
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(
|
||||
ApplicationWideMessageHolder.MessageType.FAILED_TO_IMPORT_ACCOUNT);
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> new Handler().postDelayed(() -> {
|
||||
if (getRouter().hasRootController()) {
|
||||
if (getActivity() != null) {
|
||||
getRouter().popToRoot();
|
||||
}
|
||||
} else {
|
||||
if (userUtils.anyUserExists()) {
|
||||
getRouter().setRoot(RouterTransaction.with(new ConversationsListView())
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else {
|
||||
getRouter().setRoot(RouterTransaction.with(new ServerSelectionController())
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
}
|
||||
}
|
||||
}, 7500));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -61,17 +61,17 @@ import com.facebook.imagepipeline.datasource.BaseBitmapDataSubscriber;
|
||||
import com.facebook.imagepipeline.image.CloseableImage;
|
||||
import com.facebook.imagepipeline.postprocessors.BlurPostProcessor;
|
||||
import com.facebook.imagepipeline.request.ImageRequest;
|
||||
import com.nextcloud.talk.models.RingtoneSettings;
|
||||
import com.nextcloud.talk.models.json.conversations.Conversation;
|
||||
import com.nextcloud.talk.models.json.conversations.RoomsOverall;
|
||||
import com.nextcloud.talk.models.json.participants.Participant;
|
||||
import com.nextcloud.talk.models.json.participants.ParticipantsOverall;
|
||||
import com.nextcloud.talk.R;
|
||||
import com.nextcloud.talk.api.NcApi;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.controllers.base.BaseController;
|
||||
import com.nextcloud.talk.events.ConfigurationChangeEvent;
|
||||
import com.nextcloud.talk.models.RingtoneSettings;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.models.json.conversations.Conversation;
|
||||
import com.nextcloud.talk.models.json.conversations.RoomsOverall;
|
||||
import com.nextcloud.talk.models.json.participants.Participant;
|
||||
import com.nextcloud.talk.models.json.participants.ParticipantsOverall;
|
||||
import com.nextcloud.talk.utils.ApiUtils;
|
||||
import com.nextcloud.talk.utils.DisplayUtils;
|
||||
import com.nextcloud.talk.utils.DoNotDisturbUtils;
|
||||
@ -97,397 +97,411 @@ import org.parceler.Parcels;
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class CallNotificationController extends BaseController {
|
||||
|
||||
private static final String TAG = "CallNotificationController";
|
||||
private static final String TAG = "CallNotificationController";
|
||||
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
|
||||
@Inject
|
||||
Cache cache;
|
||||
@Inject
|
||||
Cache cache;
|
||||
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
|
||||
@Inject
|
||||
Context context;
|
||||
@Inject
|
||||
Context context;
|
||||
|
||||
@BindView(R.id.conversationNameTextView)
|
||||
TextView conversationNameTextView;
|
||||
@BindView(R.id.conversationNameTextView)
|
||||
TextView conversationNameTextView;
|
||||
|
||||
@BindView(R.id.avatarImageView)
|
||||
SimpleDraweeView avatarImageView;
|
||||
@BindView(R.id.avatarImageView)
|
||||
SimpleDraweeView avatarImageView;
|
||||
|
||||
@BindView(R.id.callAnswerVoiceOnlyView)
|
||||
SimpleDraweeView callAnswerVoiceOnlyView;
|
||||
@BindView(R.id.callAnswerVoiceOnlyView)
|
||||
SimpleDraweeView callAnswerVoiceOnlyView;
|
||||
|
||||
@BindView(R.id.callAnswerCameraView)
|
||||
SimpleDraweeView callAnswerCameraView;
|
||||
@BindView(R.id.callAnswerCameraView)
|
||||
SimpleDraweeView callAnswerCameraView;
|
||||
|
||||
@BindView(R.id.backgroundImageView)
|
||||
ImageView backgroundImageView;
|
||||
@BindView(R.id.backgroundImageView)
|
||||
ImageView backgroundImageView;
|
||||
|
||||
@BindView(R.id.incomingTextRelativeLayout)
|
||||
RelativeLayout incomingTextRelativeLayout;
|
||||
@BindView(R.id.incomingTextRelativeLayout)
|
||||
RelativeLayout incomingTextRelativeLayout;
|
||||
|
||||
private Bundle originalBundle;
|
||||
private String roomId;
|
||||
private UserEntity userBeingCalled;
|
||||
private String credentials;
|
||||
private Conversation currentConversation;
|
||||
private MediaPlayer mediaPlayer;
|
||||
private boolean leavingScreen = false;
|
||||
private RenderScript renderScript;
|
||||
private Vibrator vibrator;
|
||||
private Handler handler;
|
||||
private Bundle originalBundle;
|
||||
private String roomId;
|
||||
private UserEntity userBeingCalled;
|
||||
private String credentials;
|
||||
private Conversation currentConversation;
|
||||
private MediaPlayer mediaPlayer;
|
||||
private boolean leavingScreen = false;
|
||||
private RenderScript renderScript;
|
||||
private Vibrator vibrator;
|
||||
private Handler handler;
|
||||
|
||||
public CallNotificationController(Bundle args) {
|
||||
super();
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
public CallNotificationController(Bundle args) {
|
||||
super();
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
this.roomId = args.getString(BundleKeys.INSTANCE.getKEY_ROOM_ID(), "");
|
||||
this.currentConversation = Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_ROOM()));
|
||||
this.userBeingCalled = args.getParcelable(BundleKeys.INSTANCE.getKEY_USER_ENTITY());
|
||||
this.roomId = args.getString(BundleKeys.INSTANCE.getKEY_ROOM_ID(), "");
|
||||
this.currentConversation =
|
||||
Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_ROOM()));
|
||||
this.userBeingCalled = args.getParcelable(BundleKeys.INSTANCE.getKEY_USER_ENTITY());
|
||||
|
||||
this.originalBundle = args;
|
||||
credentials = ApiUtils.getCredentials(userBeingCalled.getUsername(), userBeingCalled.getToken());
|
||||
this.originalBundle = args;
|
||||
credentials =
|
||||
ApiUtils.getCredentials(userBeingCalled.getUsername(), userBeingCalled.getToken());
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_call_notification, container, false);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDetach(@NonNull View view) {
|
||||
eventBus.unregister(this);
|
||||
super.onDetach(view);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
eventBus.register(this);
|
||||
}
|
||||
|
||||
private void showAnswerControls() {
|
||||
callAnswerCameraView.setVisibility(View.VISIBLE);
|
||||
callAnswerVoiceOnlyView.setVisibility(View.VISIBLE);
|
||||
}
|
||||
|
||||
@OnClick(R.id.callControlHangupView)
|
||||
void hangup() {
|
||||
leavingScreen = true;
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().finish();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_call_notification, container, false);
|
||||
}
|
||||
@OnClick(R.id.callAnswerCameraView)
|
||||
void answerWithCamera() {
|
||||
originalBundle.putBoolean(BundleKeys.INSTANCE.getKEY_CALL_VOICE_ONLY(), false);
|
||||
proceedToCall();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDetach(@NonNull View view) {
|
||||
eventBus.unregister(this);
|
||||
super.onDetach(view);
|
||||
}
|
||||
@OnClick(R.id.callAnswerVoiceOnlyView)
|
||||
void answerVoiceOnly() {
|
||||
originalBundle.putBoolean(BundleKeys.INSTANCE.getKEY_CALL_VOICE_ONLY(), true);
|
||||
proceedToCall();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
eventBus.register(this);
|
||||
}
|
||||
private void proceedToCall() {
|
||||
originalBundle.putString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN(),
|
||||
currentConversation.getToken());
|
||||
|
||||
private void showAnswerControls() {
|
||||
callAnswerCameraView.setVisibility(View.VISIBLE);
|
||||
callAnswerVoiceOnlyView.setVisibility(View.VISIBLE);
|
||||
}
|
||||
getRouter().replaceTopController(RouterTransaction.with(new CallController(originalBundle))
|
||||
.popChangeHandler(new HorizontalChangeHandler())
|
||||
.pushChangeHandler(new HorizontalChangeHandler()));
|
||||
}
|
||||
|
||||
@OnClick(R.id.callControlHangupView)
|
||||
void hangup() {
|
||||
leavingScreen = true;
|
||||
private void checkIfAnyParticipantsRemainInRoom() {
|
||||
ncApi.getPeersForCall(credentials, ApiUtils.getUrlForParticipants(userBeingCalled.getBaseUrl(),
|
||||
currentConversation.getToken()))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.takeWhile(observable -> !leavingScreen)
|
||||
.retry(3)
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<ParticipantsOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().finish();
|
||||
}
|
||||
}
|
||||
@Override
|
||||
public void onNext(ParticipantsOverall participantsOverall) {
|
||||
boolean hasParticipantsInCall = false;
|
||||
boolean inCallOnDifferentDevice = false;
|
||||
List<Participant> participantList = participantsOverall.getOcs().getData();
|
||||
for (Participant participant : participantList) {
|
||||
if (participant.getParticipantFlags() != Participant.ParticipantFlags.NOT_IN_CALL) {
|
||||
hasParticipantsInCall = true;
|
||||
|
||||
@OnClick(R.id.callAnswerCameraView)
|
||||
void answerWithCamera() {
|
||||
originalBundle.putBoolean(BundleKeys.INSTANCE.getKEY_CALL_VOICE_ONLY(), false);
|
||||
proceedToCall();
|
||||
}
|
||||
|
||||
@OnClick(R.id.callAnswerVoiceOnlyView)
|
||||
void answerVoiceOnly() {
|
||||
originalBundle.putBoolean(BundleKeys.INSTANCE.getKEY_CALL_VOICE_ONLY(), true);
|
||||
proceedToCall();
|
||||
}
|
||||
|
||||
private void proceedToCall() {
|
||||
originalBundle.putString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN(), currentConversation.getToken());
|
||||
|
||||
getRouter().replaceTopController(RouterTransaction.with(new CallController(originalBundle))
|
||||
.popChangeHandler(new HorizontalChangeHandler())
|
||||
.pushChangeHandler(new HorizontalChangeHandler()));
|
||||
}
|
||||
|
||||
private void checkIfAnyParticipantsRemainInRoom() {
|
||||
ncApi.getPeersForCall(credentials, ApiUtils.getUrlForParticipants(userBeingCalled.getBaseUrl(),
|
||||
currentConversation.getToken()))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.takeWhile(observable -> !leavingScreen)
|
||||
.retry(3)
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<ParticipantsOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(ParticipantsOverall participantsOverall) {
|
||||
boolean hasParticipantsInCall = false;
|
||||
boolean inCallOnDifferentDevice = false;
|
||||
List<Participant> participantList = participantsOverall.getOcs().getData();
|
||||
for (Participant participant : participantList) {
|
||||
if (participant.getParticipantFlags() != Participant.ParticipantFlags.NOT_IN_CALL) {
|
||||
hasParticipantsInCall = true;
|
||||
|
||||
if (participant.getUserId().equals(userBeingCalled.getUserId())) {
|
||||
inCallOnDifferentDevice = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!hasParticipantsInCall || inCallOnDifferentDevice) {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> hangup());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
if (!leavingScreen) {
|
||||
checkIfAnyParticipantsRemainInRoom();
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
private void handleFromNotification() {
|
||||
ncApi.getRooms(credentials, ApiUtils.getUrlForGetRooms(userBeingCalled.getBaseUrl()))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.retry(3)
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<RoomsOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(RoomsOverall roomsOverall) {
|
||||
for (Conversation conversation : roomsOverall.getOcs().getData()) {
|
||||
if (roomId.equals(conversation.getRoomId())) {
|
||||
currentConversation = conversation;
|
||||
runAllThings();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void runAllThings() {
|
||||
if (conversationNameTextView != null) {
|
||||
conversationNameTextView.setText(currentConversation.getDisplayName());
|
||||
}
|
||||
|
||||
loadAvatar();
|
||||
checkIfAnyParticipantsRemainInRoom();
|
||||
showAnswerControls();
|
||||
}
|
||||
|
||||
@SuppressLint("LongLogTag")
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
|
||||
renderScript = RenderScript.create(getActivity());
|
||||
|
||||
if (handler == null) {
|
||||
handler = new Handler();
|
||||
|
||||
try {
|
||||
cache.evictAll();
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to evict cache");
|
||||
if (participant.getUserId().equals(userBeingCalled.getUserId())) {
|
||||
inCallOnDifferentDevice = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (currentConversation == null) {
|
||||
handleFromNotification();
|
||||
if (!hasParticipantsInCall || inCallOnDifferentDevice) {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> hangup());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
if (!leavingScreen) {
|
||||
checkIfAnyParticipantsRemainInRoom();
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void handleFromNotification() {
|
||||
ncApi.getRooms(credentials, ApiUtils.getUrlForGetRooms(userBeingCalled.getBaseUrl()))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.retry(3)
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<RoomsOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(RoomsOverall roomsOverall) {
|
||||
for (Conversation conversation : roomsOverall.getOcs().getData()) {
|
||||
if (roomId.equals(conversation.getRoomId())) {
|
||||
currentConversation = conversation;
|
||||
runAllThings();
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void runAllThings() {
|
||||
if (conversationNameTextView != null) {
|
||||
conversationNameTextView.setText(currentConversation.getDisplayName());
|
||||
}
|
||||
|
||||
loadAvatar();
|
||||
checkIfAnyParticipantsRemainInRoom();
|
||||
showAnswerControls();
|
||||
}
|
||||
|
||||
@SuppressLint("LongLogTag")
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
|
||||
renderScript = RenderScript.create(getActivity());
|
||||
|
||||
if (handler == null) {
|
||||
handler = new Handler();
|
||||
|
||||
try {
|
||||
cache.evictAll();
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to evict cache");
|
||||
}
|
||||
}
|
||||
|
||||
if (currentConversation == null) {
|
||||
handleFromNotification();
|
||||
} else {
|
||||
runAllThings();
|
||||
}
|
||||
|
||||
if (DoNotDisturbUtils.INSTANCE.shouldPlaySound()) {
|
||||
String callRingtonePreferenceString = appPreferences.getCallRingtoneUri();
|
||||
Uri ringtoneUri;
|
||||
|
||||
if (TextUtils.isEmpty(callRingtonePreferenceString)) {
|
||||
// play default sound
|
||||
ringtoneUri = Uri.parse("android.resource://" + getApplicationContext().getPackageName() +
|
||||
"/raw/librem_by_feandesign_call");
|
||||
} else {
|
||||
try {
|
||||
RingtoneSettings ringtoneSettings =
|
||||
LoganSquare.parse(callRingtonePreferenceString, RingtoneSettings.class);
|
||||
ringtoneUri = ringtoneSettings.getRingtoneUri();
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to parse ringtone settings");
|
||||
ringtoneUri = Uri.parse("android.resource://" + getApplicationContext().getPackageName() +
|
||||
"/raw/librem_by_feandesign_call");
|
||||
}
|
||||
}
|
||||
|
||||
if (ringtoneUri != null && getActivity() != null) {
|
||||
mediaPlayer = new MediaPlayer();
|
||||
try {
|
||||
mediaPlayer.setDataSource(getActivity(), ringtoneUri);
|
||||
|
||||
mediaPlayer.setLooping(true);
|
||||
AudioAttributes audioAttributes =
|
||||
new AudioAttributes.Builder().setContentType(AudioAttributes
|
||||
.CONTENT_TYPE_SONIFICATION)
|
||||
.setUsage(AudioAttributes.USAGE_NOTIFICATION_RINGTONE)
|
||||
.build();
|
||||
mediaPlayer.setAudioAttributes(audioAttributes);
|
||||
|
||||
mediaPlayer.setOnPreparedListener(mp -> mediaPlayer.start());
|
||||
|
||||
mediaPlayer.prepareAsync();
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to set data source");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (DoNotDisturbUtils.INSTANCE.shouldVibrate(appPreferences.getShouldVibrateSetting())) {
|
||||
vibrator = (Vibrator) getApplicationContext().getSystemService(Context.VIBRATOR_SERVICE);
|
||||
|
||||
if (vibrator != null) {
|
||||
long[] vibratePattern = new long[] { 0, 400, 800, 600, 800, 800, 800, 1000 };
|
||||
int[] amplitudes = new int[] { 0, 255, 0, 255, 0, 255, 0, 255 };
|
||||
|
||||
VibrationEffect vibrationEffect;
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
||||
if (vibrator.hasAmplitudeControl()) {
|
||||
vibrationEffect = VibrationEffect.createWaveform(vibratePattern, amplitudes, -1);
|
||||
vibrator.vibrate(vibrationEffect);
|
||||
} else {
|
||||
vibrationEffect = VibrationEffect.createWaveform(vibratePattern, -1);
|
||||
vibrator.vibrate(vibrationEffect);
|
||||
}
|
||||
} else {
|
||||
runAllThings();
|
||||
}
|
||||
|
||||
if (DoNotDisturbUtils.INSTANCE.shouldPlaySound()) {
|
||||
String callRingtonePreferenceString = appPreferences.getCallRingtoneUri();
|
||||
Uri ringtoneUri;
|
||||
|
||||
if (TextUtils.isEmpty(callRingtonePreferenceString)) {
|
||||
// play default sound
|
||||
ringtoneUri = Uri.parse("android.resource://" + getApplicationContext().getPackageName() +
|
||||
"/raw/librem_by_feandesign_call");
|
||||
} else {
|
||||
try {
|
||||
RingtoneSettings ringtoneSettings = LoganSquare.parse(callRingtonePreferenceString, RingtoneSettings.class);
|
||||
ringtoneUri = ringtoneSettings.getRingtoneUri();
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to parse ringtone settings");
|
||||
ringtoneUri = Uri.parse("android.resource://" + getApplicationContext().getPackageName() +
|
||||
"/raw/librem_by_feandesign_call");
|
||||
}
|
||||
}
|
||||
|
||||
if (ringtoneUri != null && getActivity() != null) {
|
||||
mediaPlayer = new MediaPlayer();
|
||||
try {
|
||||
mediaPlayer.setDataSource(getActivity(), ringtoneUri);
|
||||
|
||||
mediaPlayer.setLooping(true);
|
||||
AudioAttributes audioAttributes = new AudioAttributes.Builder().setContentType(AudioAttributes
|
||||
.CONTENT_TYPE_SONIFICATION).setUsage(AudioAttributes.USAGE_NOTIFICATION_RINGTONE).build();
|
||||
mediaPlayer.setAudioAttributes(audioAttributes);
|
||||
|
||||
mediaPlayer.setOnPreparedListener(mp -> mediaPlayer.start());
|
||||
|
||||
mediaPlayer.prepareAsync();
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to set data source");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (DoNotDisturbUtils.INSTANCE.shouldVibrate(appPreferences.getShouldVibrateSetting())) {
|
||||
vibrator = (Vibrator) getApplicationContext().getSystemService(Context.VIBRATOR_SERVICE);
|
||||
|
||||
if (vibrator != null) {
|
||||
long[] vibratePattern = new long[]{0, 400, 800, 600, 800, 800, 800, 1000};
|
||||
int[] amplitudes = new int[]{0, 255, 0, 255, 0, 255, 0, 255};
|
||||
|
||||
VibrationEffect vibrationEffect;
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
||||
if (vibrator.hasAmplitudeControl()) {
|
||||
vibrationEffect = VibrationEffect.createWaveform(vibratePattern, amplitudes, -1);
|
||||
vibrator.vibrate(vibrationEffect);
|
||||
} else {
|
||||
vibrationEffect = VibrationEffect.createWaveform(vibratePattern, -1);
|
||||
vibrator.vibrate(vibrationEffect);
|
||||
}
|
||||
} else {
|
||||
vibrator.vibrate(vibratePattern, -1);
|
||||
}
|
||||
}
|
||||
|
||||
handler.postDelayed(() -> {
|
||||
if (vibrator != null) {
|
||||
vibrator.cancel();
|
||||
}
|
||||
}, 10000);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Subscribe(threadMode = ThreadMode.MAIN)
|
||||
public void onMessageEvent(ConfigurationChangeEvent configurationChangeEvent) {
|
||||
ConstraintLayout.LayoutParams layoutParams = (ConstraintLayout.LayoutParams) avatarImageView.getLayoutParams();
|
||||
int dimen = (int) getResources().getDimension(R.dimen.avatar_size_very_big);
|
||||
|
||||
layoutParams.width = dimen;
|
||||
layoutParams.height = dimen;
|
||||
avatarImageView.setLayoutParams(layoutParams);
|
||||
}
|
||||
|
||||
private void loadAvatar() {
|
||||
switch (currentConversation.getType()) {
|
||||
case ROOM_TYPE_ONE_TO_ONE_CALL:
|
||||
avatarImageView.setVisibility(View.VISIBLE);
|
||||
|
||||
ImageRequest imageRequest =
|
||||
DisplayUtils.getImageRequestForUrl(ApiUtils.getUrlForAvatarWithName(userBeingCalled.getBaseUrl(),
|
||||
currentConversation.getName(), R.dimen.avatar_size_very_big), null);
|
||||
|
||||
ImagePipeline imagePipeline = Fresco.getImagePipeline();
|
||||
DataSource<CloseableReference<CloseableImage>> dataSource = imagePipeline.fetchDecodedImage(imageRequest, null);
|
||||
|
||||
dataSource.subscribe(new BaseBitmapDataSubscriber() {
|
||||
@Override
|
||||
protected void onNewResultImpl(@Nullable Bitmap bitmap) {
|
||||
if (avatarImageView != null) {
|
||||
avatarImageView.getHierarchy().setImage(new BitmapDrawable(bitmap), 100,
|
||||
true);
|
||||
|
||||
if (getResources() != null) {
|
||||
incomingTextRelativeLayout.setBackground(getResources().getDrawable(R.drawable
|
||||
.incoming_gradient));
|
||||
}
|
||||
|
||||
if ((AvatarStatusCodeHolder.getInstance().getStatusCode() == 200 || AvatarStatusCodeHolder.getInstance().getStatusCode() == 0) &&
|
||||
userBeingCalled.hasSpreedFeatureCapability("no-ping")) {
|
||||
if (getActivity() != null) {
|
||||
Bitmap backgroundBitmap = bitmap.copy(bitmap.getConfig(), true);
|
||||
new BlurPostProcessor(5, getActivity()).process(backgroundBitmap);
|
||||
backgroundImageView.setImageDrawable(new BitmapDrawable(backgroundBitmap));
|
||||
}
|
||||
} else if (AvatarStatusCodeHolder.getInstance().getStatusCode() == 201) {
|
||||
ColorArt colorArt = new ColorArt(bitmap);
|
||||
int color = colorArt.getBackgroundColor();
|
||||
|
||||
float[] hsv = new float[3];
|
||||
Color.colorToHSV(color, hsv);
|
||||
hsv[2] *= 0.75f;
|
||||
color = Color.HSVToColor(hsv);
|
||||
|
||||
backgroundImageView.setImageDrawable(new ColorDrawable(color));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onFailureImpl(DataSource<CloseableReference<CloseableImage>> dataSource) {
|
||||
}
|
||||
}, UiThreadImmediateExecutorService.getInstance());
|
||||
|
||||
break;
|
||||
case ROOM_GROUP_CALL:
|
||||
avatarImageView.getHierarchy().setImage(DisplayUtils.getRoundedDrawable(context.getDrawable(R.drawable.ic_people_group_white_24px))
|
||||
, 100, true);
|
||||
case ROOM_PUBLIC_CALL:
|
||||
avatarImageView.getHierarchy().setImage(DisplayUtils.getRoundedDrawable(context.getDrawable(R.drawable.ic_people_group_white_24px))
|
||||
, 100, true);
|
||||
break;
|
||||
default:
|
||||
}
|
||||
}
|
||||
|
||||
private void endMediaAndVibratorNotifications() {
|
||||
if (mediaPlayer != null) {
|
||||
if (mediaPlayer.isPlaying()) {
|
||||
mediaPlayer.stop();
|
||||
}
|
||||
|
||||
mediaPlayer.release();
|
||||
mediaPlayer = null;
|
||||
vibrator.vibrate(vibratePattern, -1);
|
||||
}
|
||||
}
|
||||
|
||||
handler.postDelayed(() -> {
|
||||
if (vibrator != null) {
|
||||
vibrator.cancel();
|
||||
vibrator.cancel();
|
||||
}
|
||||
}, 10000);
|
||||
}
|
||||
}
|
||||
|
||||
@Subscribe(threadMode = ThreadMode.MAIN)
|
||||
public void onMessageEvent(ConfigurationChangeEvent configurationChangeEvent) {
|
||||
ConstraintLayout.LayoutParams layoutParams =
|
||||
(ConstraintLayout.LayoutParams) avatarImageView.getLayoutParams();
|
||||
int dimen = (int) getResources().getDimension(R.dimen.avatar_size_very_big);
|
||||
|
||||
layoutParams.width = dimen;
|
||||
layoutParams.height = dimen;
|
||||
avatarImageView.setLayoutParams(layoutParams);
|
||||
}
|
||||
|
||||
private void loadAvatar() {
|
||||
switch (currentConversation.getType()) {
|
||||
case ROOM_TYPE_ONE_TO_ONE_CALL:
|
||||
avatarImageView.setVisibility(View.VISIBLE);
|
||||
|
||||
ImageRequest imageRequest =
|
||||
DisplayUtils.getImageRequestForUrl(
|
||||
ApiUtils.getUrlForAvatarWithName(userBeingCalled.getBaseUrl(),
|
||||
currentConversation.getName(), R.dimen.avatar_size_very_big), null);
|
||||
|
||||
ImagePipeline imagePipeline = Fresco.getImagePipeline();
|
||||
DataSource<CloseableReference<CloseableImage>> dataSource =
|
||||
imagePipeline.fetchDecodedImage(imageRequest, null);
|
||||
|
||||
dataSource.subscribe(new BaseBitmapDataSubscriber() {
|
||||
@Override
|
||||
protected void onNewResultImpl(@Nullable Bitmap bitmap) {
|
||||
if (avatarImageView != null) {
|
||||
avatarImageView.getHierarchy().setImage(new BitmapDrawable(bitmap), 100,
|
||||
true);
|
||||
|
||||
if (getResources() != null) {
|
||||
incomingTextRelativeLayout.setBackground(getResources().getDrawable(R.drawable
|
||||
.incoming_gradient));
|
||||
}
|
||||
|
||||
if ((AvatarStatusCodeHolder.getInstance().getStatusCode() == 200
|
||||
|| AvatarStatusCodeHolder.getInstance().getStatusCode() == 0) &&
|
||||
userBeingCalled.hasSpreedFeatureCapability("no-ping")) {
|
||||
if (getActivity() != null) {
|
||||
Bitmap backgroundBitmap = bitmap.copy(bitmap.getConfig(), true);
|
||||
new BlurPostProcessor(5, getActivity()).process(backgroundBitmap);
|
||||
backgroundImageView.setImageDrawable(new BitmapDrawable(backgroundBitmap));
|
||||
}
|
||||
} else if (AvatarStatusCodeHolder.getInstance().getStatusCode() == 201) {
|
||||
ColorArt colorArt = new ColorArt(bitmap);
|
||||
int color = colorArt.getBackgroundColor();
|
||||
|
||||
float[] hsv = new float[3];
|
||||
Color.colorToHSV(color, hsv);
|
||||
hsv[2] *= 0.75f;
|
||||
color = Color.HSVToColor(hsv);
|
||||
|
||||
backgroundImageView.setImageDrawable(new ColorDrawable(color));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onFailureImpl(DataSource<CloseableReference<CloseableImage>> dataSource) {
|
||||
}
|
||||
}, UiThreadImmediateExecutorService.getInstance());
|
||||
|
||||
break;
|
||||
case ROOM_GROUP_CALL:
|
||||
avatarImageView.getHierarchy()
|
||||
.setImage(DisplayUtils.getRoundedDrawable(
|
||||
context.getDrawable(R.drawable.ic_people_group_white_24px))
|
||||
, 100, true);
|
||||
case ROOM_PUBLIC_CALL:
|
||||
avatarImageView.getHierarchy()
|
||||
.setImage(DisplayUtils.getRoundedDrawable(
|
||||
context.getDrawable(R.drawable.ic_people_group_white_24px))
|
||||
, 100, true);
|
||||
break;
|
||||
default:
|
||||
}
|
||||
}
|
||||
|
||||
private void endMediaAndVibratorNotifications() {
|
||||
if (mediaPlayer != null) {
|
||||
if (mediaPlayer.isPlaying()) {
|
||||
mediaPlayer.stop();
|
||||
}
|
||||
|
||||
mediaPlayer.release();
|
||||
mediaPlayer = null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
AvatarStatusCodeHolder.getInstance().setStatusCode(0);
|
||||
leavingScreen = true;
|
||||
if (handler != null) {
|
||||
handler.removeCallbacksAndMessages(null);
|
||||
handler = null;
|
||||
}
|
||||
endMediaAndVibratorNotifications();
|
||||
super.onDestroy();
|
||||
if (vibrator != null) {
|
||||
vibrator.cancel();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
AvatarStatusCodeHolder.getInstance().setStatusCode(0);
|
||||
leavingScreen = true;
|
||||
if (handler != null) {
|
||||
handler.removeCallbacksAndMessages(null);
|
||||
handler = null;
|
||||
}
|
||||
endMediaAndVibratorNotifications();
|
||||
super.onDestroy();
|
||||
}
|
||||
}
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -48,122 +48,132 @@ import javax.inject.Inject;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class LockedController extends BaseController {
|
||||
public static final String TAG = "LockedController";
|
||||
private static final int REQUEST_CODE_CONFIRM_DEVICE_CREDENTIALS = 112;
|
||||
public static final String TAG = "LockedController";
|
||||
private static final int REQUEST_CODE_CONFIRM_DEVICE_CREDENTIALS = 112;
|
||||
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_locked, container, false);
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_locked, container, false);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
if (getActionBar() != null) {
|
||||
getActionBar().hide();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
if (getActionBar() != null) {
|
||||
getActionBar().hide();
|
||||
}
|
||||
}
|
||||
@RequiresApi(api = Build.VERSION_CODES.M)
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
checkIfWeAreSecure();
|
||||
}
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.M)
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
checkIfWeAreSecure();
|
||||
}
|
||||
@RequiresApi(api = Build.VERSION_CODES.M)
|
||||
@OnClick(R.id.unlockTextView)
|
||||
void unlock() {
|
||||
checkIfWeAreSecure();
|
||||
}
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.M)
|
||||
@OnClick(R.id.unlockTextView)
|
||||
void unlock() {
|
||||
checkIfWeAreSecure();
|
||||
}
|
||||
@RequiresApi(api = Build.VERSION_CODES.M)
|
||||
private void showBiometricDialog() {
|
||||
Context context = getActivity();
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.M)
|
||||
private void showBiometricDialog() {
|
||||
Context context = getActivity();
|
||||
if (context != null) {
|
||||
final BiometricPrompt.PromptInfo promptInfo = new BiometricPrompt.PromptInfo.Builder()
|
||||
.setTitle(String.format(context.getString(R.string.nc_biometric_unlock),
|
||||
context.getString(R.string.nc_app_name)))
|
||||
.setNegativeButtonText(context.getString(R.string.nc_cancel))
|
||||
.build();
|
||||
|
||||
if (context != null) {
|
||||
final BiometricPrompt.PromptInfo promptInfo = new BiometricPrompt.PromptInfo.Builder()
|
||||
.setTitle(String.format(context.getString(R.string.nc_biometric_unlock), context.getString(R.string.nc_app_name)))
|
||||
.setNegativeButtonText(context.getString(R.string.nc_cancel))
|
||||
.build();
|
||||
Executor executor = Executors.newSingleThreadExecutor();
|
||||
|
||||
Executor executor = Executors.newSingleThreadExecutor();
|
||||
|
||||
final BiometricPrompt biometricPrompt = new BiometricPrompt((FragmentActivity) context, executor,
|
||||
new BiometricPrompt.AuthenticationCallback() {
|
||||
@Override
|
||||
public void onAuthenticationSucceeded(@NonNull BiometricPrompt.AuthenticationResult result) {
|
||||
super.onAuthenticationSucceeded(result);
|
||||
Log.d(TAG, "Fingerprint recognised successfully");
|
||||
new Handler(Looper.getMainLooper()).post(() -> getRouter().popCurrentController());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAuthenticationFailed() {
|
||||
super.onAuthenticationFailed();
|
||||
Log.d(TAG, "Fingerprint not recognised");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAuthenticationError(int errorCode, @NonNull CharSequence errString) {
|
||||
super.onAuthenticationError(errorCode, errString);
|
||||
showAuthenticationScreen();
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
BiometricPrompt.CryptoObject cryptoObject = SecurityUtils.getCryptoObject();
|
||||
if (cryptoObject != null) {
|
||||
biometricPrompt.authenticate(promptInfo, cryptoObject);
|
||||
} else {
|
||||
biometricPrompt.authenticate(promptInfo);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.M)
|
||||
private void checkIfWeAreSecure() {
|
||||
if (getActivity() != null) {
|
||||
KeyguardManager keyguardManager = (KeyguardManager) getActivity().getSystemService(Context.KEYGUARD_SERVICE);
|
||||
if (keyguardManager != null && keyguardManager.isKeyguardSecure() && appPreferences.getIsScreenLocked()) {
|
||||
if (!SecurityUtils.checkIfWeAreAuthenticated(appPreferences.getScreenLockTimeout())) {
|
||||
showBiometricDialog();
|
||||
} else {
|
||||
getRouter().popCurrentController();
|
||||
final BiometricPrompt biometricPrompt =
|
||||
new BiometricPrompt((FragmentActivity) context, executor,
|
||||
new BiometricPrompt.AuthenticationCallback() {
|
||||
@Override
|
||||
public void onAuthenticationSucceeded(
|
||||
@NonNull BiometricPrompt.AuthenticationResult result) {
|
||||
super.onAuthenticationSucceeded(result);
|
||||
Log.d(TAG, "Fingerprint recognised successfully");
|
||||
new Handler(Looper.getMainLooper()).post(
|
||||
() -> getRouter().popCurrentController());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void showAuthenticationScreen() {
|
||||
if (getActivity() != null) {
|
||||
KeyguardManager keyguardManager = (KeyguardManager) getActivity().getSystemService(Context.KEYGUARD_SERVICE);
|
||||
Intent intent = keyguardManager.createConfirmDeviceCredentialIntent(null, null);
|
||||
if (intent != null) {
|
||||
startActivityForResult(intent, REQUEST_CODE_CONFIRM_DEVICE_CREDENTIALS);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onActivityResult(int requestCode, int resultCode, Intent data) {
|
||||
super.onActivityResult(requestCode, resultCode, data);
|
||||
|
||||
if (requestCode == REQUEST_CODE_CONFIRM_DEVICE_CREDENTIALS) {
|
||||
if (resultCode == Activity.RESULT_OK) {
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
|
||||
if (SecurityUtils.checkIfWeAreAuthenticated(appPreferences.getScreenLockTimeout())) {
|
||||
Log.d(TAG, "All went well, dismiss locked controller");
|
||||
getRouter().popCurrentController();
|
||||
}
|
||||
@Override
|
||||
public void onAuthenticationFailed() {
|
||||
super.onAuthenticationFailed();
|
||||
Log.d(TAG, "Fingerprint not recognised");
|
||||
}
|
||||
} else {
|
||||
Log.d(TAG, "Authorization failed");
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAuthenticationError(int errorCode, @NonNull CharSequence errString) {
|
||||
super.onAuthenticationError(errorCode, errString);
|
||||
showAuthenticationScreen();
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
BiometricPrompt.CryptoObject cryptoObject = SecurityUtils.getCryptoObject();
|
||||
if (cryptoObject != null) {
|
||||
biometricPrompt.authenticate(promptInfo, cryptoObject);
|
||||
} else {
|
||||
biometricPrompt.authenticate(promptInfo);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@RequiresApi(api = Build.VERSION_CODES.M)
|
||||
private void checkIfWeAreSecure() {
|
||||
if (getActivity() != null) {
|
||||
KeyguardManager keyguardManager =
|
||||
(KeyguardManager) getActivity().getSystemService(Context.KEYGUARD_SERVICE);
|
||||
if (keyguardManager != null
|
||||
&& keyguardManager.isKeyguardSecure()
|
||||
&& appPreferences.getIsScreenLocked()) {
|
||||
if (!SecurityUtils.checkIfWeAreAuthenticated(appPreferences.getScreenLockTimeout())) {
|
||||
showBiometricDialog();
|
||||
} else {
|
||||
getRouter().popCurrentController();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void showAuthenticationScreen() {
|
||||
if (getActivity() != null) {
|
||||
KeyguardManager keyguardManager =
|
||||
(KeyguardManager) getActivity().getSystemService(Context.KEYGUARD_SERVICE);
|
||||
Intent intent = keyguardManager.createConfirmDeviceCredentialIntent(null, null);
|
||||
if (intent != null) {
|
||||
startActivityForResult(intent, REQUEST_CODE_CONFIRM_DEVICE_CREDENTIALS);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onActivityResult(int requestCode, int resultCode, Intent data) {
|
||||
super.onActivityResult(requestCode, resultCode, data);
|
||||
|
||||
if (requestCode == REQUEST_CODE_CONFIRM_DEVICE_CREDENTIALS) {
|
||||
if (resultCode == Activity.RESULT_OK) {
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
|
||||
if (SecurityUtils.checkIfWeAreAuthenticated(appPreferences.getScreenLockTimeout())) {
|
||||
Log.d(TAG, "All went well, dismiss locked controller");
|
||||
getRouter().popCurrentController();
|
||||
}
|
||||
}
|
||||
} else {
|
||||
Log.d(TAG, "Authorization failed");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -40,11 +40,11 @@ import androidx.swiperefreshlayout.widget.SwipeRefreshLayout;
|
||||
import autodagger.AutoInjector;
|
||||
import butterknife.BindView;
|
||||
import com.bluelinelabs.logansquare.LoganSquare;
|
||||
import com.nextcloud.talk.models.RingtoneSettings;
|
||||
import com.nextcloud.talk.R;
|
||||
import com.nextcloud.talk.adapters.items.NotificationSoundItem;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.controllers.base.BaseController;
|
||||
import com.nextcloud.talk.models.RingtoneSettings;
|
||||
import com.nextcloud.talk.utils.bundle.BundleKeys;
|
||||
import com.nextcloud.talk.utils.preferences.AppPreferences;
|
||||
import eu.davidea.flexibleadapter.FlexibleAdapter;
|
||||
@ -57,247 +57,255 @@ import java.util.List;
|
||||
import javax.inject.Inject;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class RingtoneSelectionController extends BaseController implements FlexibleAdapter.OnItemClickListener {
|
||||
public class RingtoneSelectionController extends BaseController
|
||||
implements FlexibleAdapter.OnItemClickListener {
|
||||
|
||||
private static final String TAG = "RingtoneSelectionController";
|
||||
private static final String TAG = "RingtoneSelectionController";
|
||||
|
||||
@BindView(R.id.recyclerView)
|
||||
RecyclerView recyclerView;
|
||||
@BindView(R.id.recyclerView)
|
||||
RecyclerView recyclerView;
|
||||
|
||||
@BindView(R.id.swipe_refresh_layout)
|
||||
SwipeRefreshLayout swipeRefreshLayout;
|
||||
@BindView(R.id.swipe_refresh_layout)
|
||||
SwipeRefreshLayout swipeRefreshLayout;
|
||||
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
|
||||
@Inject
|
||||
Context context;
|
||||
@Inject
|
||||
Context context;
|
||||
|
||||
private FlexibleAdapter adapter;
|
||||
private RecyclerView.AdapterDataObserver adapterDataObserver;
|
||||
private List<AbstractFlexibleItem> abstractFlexibleItemList = new ArrayList<>();
|
||||
private FlexibleAdapter adapter;
|
||||
private RecyclerView.AdapterDataObserver adapterDataObserver;
|
||||
private List<AbstractFlexibleItem> abstractFlexibleItemList = new ArrayList<>();
|
||||
|
||||
private boolean callNotificationSounds;
|
||||
private MediaPlayer mediaPlayer;
|
||||
private Handler cancelMediaPlayerHandler;
|
||||
private boolean callNotificationSounds;
|
||||
private MediaPlayer mediaPlayer;
|
||||
private Handler cancelMediaPlayerHandler;
|
||||
|
||||
public RingtoneSelectionController(Bundle args) {
|
||||
super();
|
||||
setHasOptionsMenu(true);
|
||||
this.callNotificationSounds = args.getBoolean(BundleKeys.INSTANCE.getKEY_ARE_CALL_SOUNDS(), false);
|
||||
public RingtoneSelectionController(Bundle args) {
|
||||
super();
|
||||
setHasOptionsMenu(true);
|
||||
this.callNotificationSounds =
|
||||
args.getBoolean(BundleKeys.INSTANCE.getKEY_ARE_CALL_SOUNDS(), false);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_generic_rv, container, false);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
if (adapter == null) {
|
||||
adapter = new FlexibleAdapter<>(abstractFlexibleItemList, getActivity(), false);
|
||||
|
||||
adapter.setNotifyChangeOfUnfilteredItems(true)
|
||||
.setMode(SelectableAdapter.Mode.SINGLE);
|
||||
|
||||
adapter.addListener(this);
|
||||
|
||||
cancelMediaPlayerHandler = new Handler();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_generic_rv, container, false);
|
||||
adapter.addListener(this);
|
||||
prepareViews();
|
||||
fetchNotificationSounds();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onOptionsItemSelected(@NonNull MenuItem item) {
|
||||
switch (item.getItemId()) {
|
||||
case android.R.id.home:
|
||||
return getRouter().popCurrentController();
|
||||
default:
|
||||
return super.onOptionsItemSelected(item);
|
||||
}
|
||||
}
|
||||
|
||||
private void prepareViews() {
|
||||
RecyclerView.LayoutManager layoutManager = new SmoothScrollLinearLayoutManager(getActivity());
|
||||
recyclerView.setLayoutManager(layoutManager);
|
||||
recyclerView.setHasFixedSize(true);
|
||||
recyclerView.setAdapter(adapter);
|
||||
|
||||
adapterDataObserver = new RecyclerView.AdapterDataObserver() {
|
||||
@Override
|
||||
public void onChanged() {
|
||||
super.onChanged();
|
||||
findSelectedSound();
|
||||
}
|
||||
};
|
||||
|
||||
adapter.registerAdapterDataObserver(adapterDataObserver);
|
||||
swipeRefreshLayout.setEnabled(false);
|
||||
}
|
||||
|
||||
@SuppressLint("LongLogTag")
|
||||
private void findSelectedSound() {
|
||||
boolean foundDefault = false;
|
||||
|
||||
String preferencesString = null;
|
||||
if ((callNotificationSounds && TextUtils.isEmpty(
|
||||
(preferencesString = appPreferences.getCallRingtoneUri())))
|
||||
|| (!callNotificationSounds && TextUtils.isEmpty((preferencesString = appPreferences
|
||||
.getMessageRingtoneUri())))) {
|
||||
adapter.toggleSelection(1);
|
||||
foundDefault = true;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
|
||||
if (adapter == null) {
|
||||
adapter = new FlexibleAdapter<>(abstractFlexibleItemList, getActivity(), false);
|
||||
|
||||
adapter.setNotifyChangeOfUnfilteredItems(true)
|
||||
.setMode(SelectableAdapter.Mode.SINGLE);
|
||||
|
||||
adapter.addListener(this);
|
||||
|
||||
cancelMediaPlayerHandler = new Handler();
|
||||
}
|
||||
|
||||
adapter.addListener(this);
|
||||
prepareViews();
|
||||
fetchNotificationSounds();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onOptionsItemSelected(@NonNull MenuItem item) {
|
||||
switch (item.getItemId()) {
|
||||
case android.R.id.home:
|
||||
return getRouter().popCurrentController();
|
||||
default:
|
||||
return super.onOptionsItemSelected(item);
|
||||
}
|
||||
}
|
||||
|
||||
private void prepareViews() {
|
||||
RecyclerView.LayoutManager layoutManager = new SmoothScrollLinearLayoutManager(getActivity());
|
||||
recyclerView.setLayoutManager(layoutManager);
|
||||
recyclerView.setHasFixedSize(true);
|
||||
recyclerView.setAdapter(adapter);
|
||||
|
||||
adapterDataObserver = new RecyclerView.AdapterDataObserver() {
|
||||
@Override
|
||||
public void onChanged() {
|
||||
super.onChanged();
|
||||
findSelectedSound();
|
||||
}
|
||||
};
|
||||
|
||||
adapter.registerAdapterDataObserver(adapterDataObserver);
|
||||
swipeRefreshLayout.setEnabled(false);
|
||||
}
|
||||
|
||||
@SuppressLint("LongLogTag")
|
||||
private void findSelectedSound() {
|
||||
boolean foundDefault = false;
|
||||
|
||||
String preferencesString = null;
|
||||
if ((callNotificationSounds && TextUtils.isEmpty((preferencesString = appPreferences.getCallRingtoneUri())))
|
||||
|| (!callNotificationSounds && TextUtils.isEmpty((preferencesString = appPreferences
|
||||
.getMessageRingtoneUri())))) {
|
||||
adapter.toggleSelection(1);
|
||||
foundDefault = true;
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(preferencesString) && !foundDefault) {
|
||||
try {
|
||||
RingtoneSettings ringtoneSettings = LoganSquare.parse(preferencesString, RingtoneSettings.class);
|
||||
if (ringtoneSettings.getRingtoneUri() == null) {
|
||||
adapter.toggleSelection(0);
|
||||
} else if (ringtoneSettings.getRingtoneUri().toString().equals(getRingtoneString())) {
|
||||
adapter.toggleSelection(1);
|
||||
} else {
|
||||
NotificationSoundItem notificationSoundItem;
|
||||
for (int i = 2; i < adapter.getItemCount(); i++) {
|
||||
notificationSoundItem = (NotificationSoundItem) adapter.getItem(i);
|
||||
if (notificationSoundItem.getNotificationSoundUri().equals(ringtoneSettings.getRingtoneUri().toString())) {
|
||||
adapter.toggleSelection(i);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to parse ringtone settings");
|
||||
}
|
||||
}
|
||||
|
||||
adapter.unregisterAdapterDataObserver(adapterDataObserver);
|
||||
adapterDataObserver = null;
|
||||
}
|
||||
|
||||
private String getRingtoneString() {
|
||||
if (callNotificationSounds) {
|
||||
return ("android.resource://" + context.getPackageName() +
|
||||
"/raw/librem_by_feandesign_call");
|
||||
if (!TextUtils.isEmpty(preferencesString) && !foundDefault) {
|
||||
try {
|
||||
RingtoneSettings ringtoneSettings =
|
||||
LoganSquare.parse(preferencesString, RingtoneSettings.class);
|
||||
if (ringtoneSettings.getRingtoneUri() == null) {
|
||||
adapter.toggleSelection(0);
|
||||
} else if (ringtoneSettings.getRingtoneUri().toString().equals(getRingtoneString())) {
|
||||
adapter.toggleSelection(1);
|
||||
} else {
|
||||
return ("android.resource://" + context.getPackageName() + "/raw" +
|
||||
"/librem_by_feandesign_message");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void fetchNotificationSounds() {
|
||||
abstractFlexibleItemList.add(new NotificationSoundItem(getResources().getString(R.string.nc_settings_no_ringtone), null));
|
||||
abstractFlexibleItemList.add(new NotificationSoundItem(getResources()
|
||||
.getString(R.string.nc_settings_default_ringtone), getRingtoneString()));
|
||||
|
||||
|
||||
if (getActivity() != null) {
|
||||
RingtoneManager manager = new RingtoneManager(getActivity());
|
||||
|
||||
if (callNotificationSounds) {
|
||||
manager.setType(RingtoneManager.TYPE_RINGTONE);
|
||||
} else {
|
||||
manager.setType(RingtoneManager.TYPE_NOTIFICATION);
|
||||
}
|
||||
|
||||
Cursor cursor = manager.getCursor();
|
||||
|
||||
NotificationSoundItem notificationSoundItem;
|
||||
|
||||
while (cursor.moveToNext()) {
|
||||
String notificationTitle = cursor.getString(RingtoneManager.TITLE_COLUMN_INDEX);
|
||||
String notificationUri = cursor.getString(RingtoneManager.URI_COLUMN_INDEX);
|
||||
String completeNotificationUri = notificationUri + "/" + cursor.getString(RingtoneManager
|
||||
.ID_COLUMN_INDEX);
|
||||
|
||||
notificationSoundItem = new NotificationSoundItem(notificationTitle, completeNotificationUri);
|
||||
|
||||
abstractFlexibleItemList.add(notificationSoundItem);
|
||||
NotificationSoundItem notificationSoundItem;
|
||||
for (int i = 2; i < adapter.getItemCount(); i++) {
|
||||
notificationSoundItem = (NotificationSoundItem) adapter.getItem(i);
|
||||
if (notificationSoundItem.getNotificationSoundUri()
|
||||
.equals(ringtoneSettings.getRingtoneUri().toString())) {
|
||||
adapter.toggleSelection(i);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
adapter.updateDataSet(abstractFlexibleItemList, false);
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to parse ringtone settings");
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getTitle() {
|
||||
return getResources().getString(R.string.nc_settings_notification_sounds);
|
||||
adapter.unregisterAdapterDataObserver(adapterDataObserver);
|
||||
adapterDataObserver = null;
|
||||
}
|
||||
|
||||
private String getRingtoneString() {
|
||||
if (callNotificationSounds) {
|
||||
return ("android.resource://" + context.getPackageName() +
|
||||
"/raw/librem_by_feandesign_call");
|
||||
} else {
|
||||
return ("android.resource://" + context.getPackageName() + "/raw" +
|
||||
"/librem_by_feandesign_message");
|
||||
}
|
||||
}
|
||||
|
||||
private void fetchNotificationSounds() {
|
||||
abstractFlexibleItemList.add(
|
||||
new NotificationSoundItem(getResources().getString(R.string.nc_settings_no_ringtone),
|
||||
null));
|
||||
abstractFlexibleItemList.add(new NotificationSoundItem(getResources()
|
||||
.getString(R.string.nc_settings_default_ringtone), getRingtoneString()));
|
||||
|
||||
if (getActivity() != null) {
|
||||
RingtoneManager manager = new RingtoneManager(getActivity());
|
||||
|
||||
if (callNotificationSounds) {
|
||||
manager.setType(RingtoneManager.TYPE_RINGTONE);
|
||||
} else {
|
||||
manager.setType(RingtoneManager.TYPE_NOTIFICATION);
|
||||
}
|
||||
|
||||
Cursor cursor = manager.getCursor();
|
||||
|
||||
NotificationSoundItem notificationSoundItem;
|
||||
|
||||
while (cursor.moveToNext()) {
|
||||
String notificationTitle = cursor.getString(RingtoneManager.TITLE_COLUMN_INDEX);
|
||||
String notificationUri = cursor.getString(RingtoneManager.URI_COLUMN_INDEX);
|
||||
String completeNotificationUri = notificationUri + "/" + cursor.getString(RingtoneManager
|
||||
.ID_COLUMN_INDEX);
|
||||
|
||||
notificationSoundItem =
|
||||
new NotificationSoundItem(notificationTitle, completeNotificationUri);
|
||||
|
||||
abstractFlexibleItemList.add(notificationSoundItem);
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressLint("LongLogTag")
|
||||
@Override
|
||||
public boolean onItemClick(View view, int position) {
|
||||
NotificationSoundItem notificationSoundItem = (NotificationSoundItem) adapter.getItem(position);
|
||||
adapter.updateDataSet(abstractFlexibleItemList, false);
|
||||
}
|
||||
|
||||
Uri ringtoneUri = null;
|
||||
@Override
|
||||
public String getTitle() {
|
||||
return getResources().getString(R.string.nc_settings_notification_sounds);
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(notificationSoundItem.getNotificationSoundUri())) {
|
||||
ringtoneUri = Uri.parse(notificationSoundItem.getNotificationSoundUri());
|
||||
@SuppressLint("LongLogTag")
|
||||
@Override
|
||||
public boolean onItemClick(View view, int position) {
|
||||
NotificationSoundItem notificationSoundItem = (NotificationSoundItem) adapter.getItem(position);
|
||||
|
||||
endMediaPlayer();
|
||||
mediaPlayer = MediaPlayer.create(getActivity(), ringtoneUri);
|
||||
Uri ringtoneUri = null;
|
||||
|
||||
cancelMediaPlayerHandler = new Handler();
|
||||
cancelMediaPlayerHandler.postDelayed(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
endMediaPlayer();
|
||||
}
|
||||
}, mediaPlayer.getDuration() + 25);
|
||||
mediaPlayer.start();
|
||||
if (!TextUtils.isEmpty(notificationSoundItem.getNotificationSoundUri())) {
|
||||
ringtoneUri = Uri.parse(notificationSoundItem.getNotificationSoundUri());
|
||||
|
||||
endMediaPlayer();
|
||||
mediaPlayer = MediaPlayer.create(getActivity(), ringtoneUri);
|
||||
|
||||
cancelMediaPlayerHandler = new Handler();
|
||||
cancelMediaPlayerHandler.postDelayed(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
endMediaPlayer();
|
||||
}
|
||||
|
||||
if (adapter.getSelectedPositions().size() == 0 || adapter.getSelectedPositions().get(0) != position) {
|
||||
RingtoneSettings ringtoneSettings = new RingtoneSettings();
|
||||
ringtoneSettings.setRingtoneName(notificationSoundItem.getNotificationSoundName());
|
||||
ringtoneSettings.setRingtoneUri(ringtoneUri);
|
||||
|
||||
if (callNotificationSounds) {
|
||||
try {
|
||||
appPreferences.setCallRingtoneUri(LoganSquare.serialize(ringtoneSettings));
|
||||
adapter.toggleSelection(position);
|
||||
adapter.notifyDataSetChanged();
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to store selected ringtone for calls");
|
||||
}
|
||||
} else {
|
||||
try {
|
||||
appPreferences.setMessageRingtoneUri(LoganSquare.serialize(ringtoneSettings));
|
||||
adapter.toggleSelection(position);
|
||||
adapter.notifyDataSetChanged();
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to store selected ringtone for calls");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}, mediaPlayer.getDuration() + 25);
|
||||
mediaPlayer.start();
|
||||
}
|
||||
|
||||
private void endMediaPlayer() {
|
||||
if (cancelMediaPlayerHandler != null) {
|
||||
cancelMediaPlayerHandler.removeCallbacksAndMessages(null);
|
||||
}
|
||||
if (adapter.getSelectedPositions().size() == 0
|
||||
|| adapter.getSelectedPositions().get(0) != position) {
|
||||
RingtoneSettings ringtoneSettings = new RingtoneSettings();
|
||||
ringtoneSettings.setRingtoneName(notificationSoundItem.getNotificationSoundName());
|
||||
ringtoneSettings.setRingtoneUri(ringtoneUri);
|
||||
|
||||
if (mediaPlayer != null) {
|
||||
if (mediaPlayer.isPlaying()) {
|
||||
mediaPlayer.stop();
|
||||
}
|
||||
|
||||
mediaPlayer.release();
|
||||
mediaPlayer = null;
|
||||
if (callNotificationSounds) {
|
||||
try {
|
||||
appPreferences.setCallRingtoneUri(LoganSquare.serialize(ringtoneSettings));
|
||||
adapter.toggleSelection(position);
|
||||
adapter.notifyDataSetChanged();
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to store selected ringtone for calls");
|
||||
}
|
||||
} else {
|
||||
try {
|
||||
appPreferences.setMessageRingtoneUri(LoganSquare.serialize(ringtoneSettings));
|
||||
adapter.toggleSelection(position);
|
||||
adapter.notifyDataSetChanged();
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to store selected ringtone for calls");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
endMediaPlayer();
|
||||
super.onDestroy();
|
||||
return true;
|
||||
}
|
||||
|
||||
private void endMediaPlayer() {
|
||||
if (cancelMediaPlayerHandler != null) {
|
||||
cancelMediaPlayerHandler.removeCallbacksAndMessages(null);
|
||||
}
|
||||
|
||||
if (mediaPlayer != null) {
|
||||
if (mediaPlayer.isPlaying()) {
|
||||
mediaPlayer.stop();
|
||||
}
|
||||
|
||||
mediaPlayer.release();
|
||||
mediaPlayer = null;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
endMediaPlayer();
|
||||
super.onDestroy();
|
||||
}
|
||||
}
|
||||
|
@ -62,301 +62,309 @@ import studio.carbonylgroup.textfieldboxes.TextFieldBoxes;
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class ServerSelectionController extends BaseController {
|
||||
|
||||
public static final String TAG = "ServerSelectionController";
|
||||
public static final String TAG = "ServerSelectionController";
|
||||
|
||||
@BindView(R.id.extended_edit_text)
|
||||
ExtendedEditText serverEntry;
|
||||
@BindView(R.id.text_field_boxes)
|
||||
TextFieldBoxes textFieldBoxes;
|
||||
@BindView(R.id.progress_bar)
|
||||
ProgressBar progressBar;
|
||||
@BindView(R.id.helper_text_view)
|
||||
TextView providersTextView;
|
||||
@BindView(R.id.cert_text_view)
|
||||
TextView certTextView;
|
||||
@BindView(R.id.extended_edit_text)
|
||||
ExtendedEditText serverEntry;
|
||||
@BindView(R.id.text_field_boxes)
|
||||
TextFieldBoxes textFieldBoxes;
|
||||
@BindView(R.id.progress_bar)
|
||||
ProgressBar progressBar;
|
||||
@BindView(R.id.helper_text_view)
|
||||
TextView providersTextView;
|
||||
@BindView(R.id.cert_text_view)
|
||||
TextView certTextView;
|
||||
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_server_selection, container, false);
|
||||
}
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_server_selection, container, false);
|
||||
}
|
||||
|
||||
@SuppressLint("LongLogTag")
|
||||
@OnClick(R.id.cert_text_view)
|
||||
public void onCertClick() {
|
||||
if (getActivity() != null) {
|
||||
KeyChain.choosePrivateKeyAlias(getActivity(), alias -> {
|
||||
if (alias != null) {
|
||||
appPreferences.setTemporaryClientCertAlias(alias);
|
||||
} else {
|
||||
appPreferences.removeTemporaryClientCertAlias();
|
||||
}
|
||||
|
||||
setCertTextView();
|
||||
}, new String[]{"RSA", "EC"}, null, null, -1, null);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
|
||||
}
|
||||
|
||||
if (getActionBar() != null) {
|
||||
getActionBar().hide();
|
||||
}
|
||||
|
||||
textFieldBoxes.getEndIconImageButton().setBackgroundDrawable(getResources().getDrawable(R.drawable
|
||||
.ic_arrow_forward_white_24px));
|
||||
textFieldBoxes.getEndIconImageButton().setAlpha(0.5f);
|
||||
textFieldBoxes.getEndIconImageButton().setEnabled(false);
|
||||
textFieldBoxes.getEndIconImageButton().setVisibility(View.VISIBLE);
|
||||
textFieldBoxes.getEndIconImageButton().setOnClickListener(view1 -> checkServerAndProceed());
|
||||
|
||||
if (TextUtils.isEmpty(getResources().getString(R.string.nc_providers_url)) && (TextUtils.isEmpty(getResources
|
||||
().getString(R.string.nc_import_account_type)))) {
|
||||
providersTextView.setVisibility(View.INVISIBLE);
|
||||
@SuppressLint("LongLogTag")
|
||||
@OnClick(R.id.cert_text_view)
|
||||
public void onCertClick() {
|
||||
if (getActivity() != null) {
|
||||
KeyChain.choosePrivateKeyAlias(getActivity(), alias -> {
|
||||
if (alias != null) {
|
||||
appPreferences.setTemporaryClientCertAlias(alias);
|
||||
} else {
|
||||
if ((TextUtils.isEmpty(getResources
|
||||
().getString(R.string.nc_import_account_type)) ||
|
||||
AccountUtils.INSTANCE.findAccounts(userUtils.getUsers()).size() == 0) &&
|
||||
userUtils.getUsers().size() == 0) {
|
||||
|
||||
providersTextView.setText(R.string.nc_get_from_provider);
|
||||
providersTextView.setOnClickListener(view12 -> {
|
||||
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(getResources()
|
||||
.getString(R.string.nc_providers_url)));
|
||||
startActivity(browserIntent);
|
||||
});
|
||||
} else if (AccountUtils.INSTANCE.findAccounts(userUtils.getUsers()).size() > 0) {
|
||||
if (!TextUtils.isEmpty(AccountUtils.INSTANCE.getAppNameBasedOnPackage(getResources()
|
||||
.getString(R.string.nc_import_accounts_from)))) {
|
||||
if (AccountUtils.INSTANCE.findAccounts(userUtils.getUsers()).size() > 1) {
|
||||
providersTextView.setText(String.format(getResources().getString(R.string
|
||||
.nc_server_import_accounts), AccountUtils.INSTANCE.getAppNameBasedOnPackage(getResources()
|
||||
.getString(R.string.nc_import_accounts_from))));
|
||||
} else {
|
||||
providersTextView.setText(String.format(getResources().getString(R.string
|
||||
.nc_server_import_account), AccountUtils.INSTANCE.getAppNameBasedOnPackage(getResources()
|
||||
.getString(R.string.nc_import_accounts_from))));
|
||||
}
|
||||
} else {
|
||||
if (AccountUtils.INSTANCE.findAccounts(userUtils.getUsers()).size() > 1) {
|
||||
providersTextView.setText(getResources().getString(R.string.nc_server_import_accounts_plain));
|
||||
} else {
|
||||
providersTextView.setText(getResources().getString(R.string
|
||||
.nc_server_import_account_plain));
|
||||
}
|
||||
}
|
||||
|
||||
providersTextView.setOnClickListener(view13 -> {
|
||||
Bundle bundle = new Bundle();
|
||||
bundle.putBoolean(BundleKeys.INSTANCE.getKEY_IS_ACCOUNT_IMPORT(), true);
|
||||
getRouter().pushController(RouterTransaction.with(
|
||||
new SwitchAccountController(bundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
});
|
||||
} else {
|
||||
providersTextView.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
}
|
||||
|
||||
serverEntry.requestFocus();
|
||||
|
||||
serverEntry.addTextChangedListener(new TextWatcher() {
|
||||
@Override
|
||||
public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterTextChanged(Editable editable) {
|
||||
if (!textFieldBoxes.isOnError() && !TextUtils.isEmpty(serverEntry.getText())) {
|
||||
toggleProceedButton(true);
|
||||
} else {
|
||||
toggleProceedButton(false);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
serverEntry.setOnEditorActionListener((textView, i, keyEvent) -> {
|
||||
if (i == EditorInfo.IME_ACTION_DONE) {
|
||||
checkServerAndProceed();
|
||||
}
|
||||
|
||||
return false;
|
||||
});
|
||||
}
|
||||
|
||||
private void toggleProceedButton(boolean show) {
|
||||
textFieldBoxes.getEndIconImageButton().setEnabled(show);
|
||||
|
||||
if (show) {
|
||||
textFieldBoxes.getEndIconImageButton().setAlpha(1f);
|
||||
} else {
|
||||
textFieldBoxes.getEndIconImageButton().setAlpha(0.5f);
|
||||
}
|
||||
}
|
||||
|
||||
private void checkServerAndProceed() {
|
||||
String url = serverEntry.getText().toString().trim();
|
||||
|
||||
serverEntry.setEnabled(false);
|
||||
progressBar.setVisibility(View.VISIBLE);
|
||||
if (providersTextView.getVisibility() != View.INVISIBLE) {
|
||||
providersTextView.setVisibility(View.INVISIBLE);
|
||||
certTextView.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
|
||||
if (url.endsWith("/")) {
|
||||
url = url.substring(0, url.length() - 1);
|
||||
}
|
||||
|
||||
String queryUrl = url + ApiUtils.getUrlPostfixForStatus();
|
||||
|
||||
if (url.startsWith("http://") || url.startsWith("https://")) {
|
||||
checkServer(queryUrl, false);
|
||||
} else {
|
||||
checkServer("https://" + queryUrl, true);
|
||||
}
|
||||
}
|
||||
|
||||
private void checkServer(String queryUrl, boolean checkForcedHttps) {
|
||||
ncApi.getServerStatus(queryUrl)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(status -> {
|
||||
String productName = getResources().getString(R.string.nc_server_product_name);
|
||||
|
||||
String versionString = status.getVersion().substring(0, status.getVersion().indexOf("."));
|
||||
int version = Integer.parseInt(versionString);
|
||||
if (status.isInstalled() && !status.isMaintenance() &&
|
||||
!status.isNeedsUpgrade() &&
|
||||
version >= 13) {
|
||||
|
||||
getRouter().pushController(RouterTransaction.with(
|
||||
new WebViewLoginController(queryUrl.replace("/status.php", ""),
|
||||
false))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else if (!status.isInstalled()) {
|
||||
textFieldBoxes.setError(String.format(
|
||||
getResources().getString(R.string.nc_server_not_installed), productName),
|
||||
true);
|
||||
toggleProceedButton(false);
|
||||
} else if (status.isNeedsUpgrade()) {
|
||||
textFieldBoxes.setError(String.format(getResources().
|
||||
getString(R.string.nc_server_db_upgrade_needed),
|
||||
productName), true);
|
||||
toggleProceedButton(false);
|
||||
} else if (status.isMaintenance()) {
|
||||
textFieldBoxes.setError(String.format(getResources().
|
||||
getString(R.string.nc_server_maintenance),
|
||||
productName),
|
||||
true);
|
||||
toggleProceedButton(false);
|
||||
} else if (!status.getVersion().startsWith("13.")) {
|
||||
textFieldBoxes.setError(String.format(getResources().
|
||||
getString(R.string.nc_server_version),
|
||||
getResources().getString(R.string.nc_app_name)
|
||||
, productName), true);
|
||||
toggleProceedButton(false);
|
||||
}
|
||||
|
||||
}, throwable -> {
|
||||
if (checkForcedHttps) {
|
||||
checkServer(queryUrl.replace("https://", "http://"), false);
|
||||
} else {
|
||||
if (throwable.getLocalizedMessage() != null) {
|
||||
textFieldBoxes.setError(throwable.getLocalizedMessage(), true);
|
||||
} else if (throwable.getCause() instanceof CertificateException) {
|
||||
textFieldBoxes.setError(getResources().getString(R.string.nc_certificate_error),
|
||||
false);
|
||||
}
|
||||
|
||||
if (serverEntry != null) {
|
||||
serverEntry.setEnabled(true);
|
||||
}
|
||||
|
||||
progressBar.setVisibility(View.INVISIBLE);
|
||||
if (providersTextView.getVisibility() != View.INVISIBLE) {
|
||||
providersTextView.setVisibility(View.VISIBLE);
|
||||
certTextView.setVisibility(View.VISIBLE);
|
||||
}
|
||||
toggleProceedButton(false);
|
||||
}
|
||||
}, () -> {
|
||||
progressBar.setVisibility(View.INVISIBLE);
|
||||
if (providersTextView.getVisibility() != View.INVISIBLE) {
|
||||
providersTextView.setVisibility(View.VISIBLE);
|
||||
certTextView.setVisibility(View.VISIBLE);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
if (ApplicationWideMessageHolder.getInstance().getMessageType() != null) {
|
||||
if (ApplicationWideMessageHolder.getInstance().getMessageType()
|
||||
.equals(ApplicationWideMessageHolder.MessageType.ACCOUNT_SCHEDULED_FOR_DELETION)) {
|
||||
textFieldBoxes.setError(getResources().getString(R.string.nc_account_scheduled_for_deletion),
|
||||
false);
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(null);
|
||||
} else if (ApplicationWideMessageHolder.getInstance().getMessageType()
|
||||
.equals(ApplicationWideMessageHolder.MessageType.SERVER_WITHOUT_TALK)) {
|
||||
textFieldBoxes.setError(getResources().getString(R.string.nc_settings_no_talk_installed),
|
||||
false);
|
||||
} else if (ApplicationWideMessageHolder.getInstance().getMessageType()
|
||||
.equals(ApplicationWideMessageHolder.MessageType.FAILED_TO_IMPORT_ACCOUNT)) {
|
||||
textFieldBoxes.setError(getResources().getString(R.string.nc_server_failed_to_import_account),
|
||||
false);
|
||||
}
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(null);
|
||||
appPreferences.removeTemporaryClientCertAlias();
|
||||
}
|
||||
|
||||
setCertTextView();
|
||||
}, new String[] { "RSA", "EC" }, null, null, -1, null);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
|
||||
}
|
||||
|
||||
private void setCertTextView() {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> {
|
||||
if (!TextUtils.isEmpty(appPreferences.getTemporaryClientCertAlias())) {
|
||||
certTextView.setText(R.string.nc_change_cert_auth);
|
||||
} else {
|
||||
certTextView.setText(R.string.nc_configure_cert_auth);
|
||||
}
|
||||
if (getActionBar() != null) {
|
||||
getActionBar().hide();
|
||||
}
|
||||
|
||||
textFieldBoxes.setError("", true);
|
||||
toggleProceedButton(true);
|
||||
});
|
||||
textFieldBoxes.getEndIconImageButton()
|
||||
.setBackgroundDrawable(getResources().getDrawable(R.drawable
|
||||
.ic_arrow_forward_white_24px));
|
||||
textFieldBoxes.getEndIconImageButton().setAlpha(0.5f);
|
||||
textFieldBoxes.getEndIconImageButton().setEnabled(false);
|
||||
textFieldBoxes.getEndIconImageButton().setVisibility(View.VISIBLE);
|
||||
textFieldBoxes.getEndIconImageButton().setOnClickListener(view1 -> checkServerAndProceed());
|
||||
|
||||
if (TextUtils.isEmpty(getResources().getString(R.string.nc_providers_url))
|
||||
&& (TextUtils.isEmpty(getResources
|
||||
().getString(R.string.nc_import_account_type)))) {
|
||||
providersTextView.setVisibility(View.INVISIBLE);
|
||||
} else {
|
||||
if ((TextUtils.isEmpty(getResources
|
||||
().getString(R.string.nc_import_account_type)) ||
|
||||
AccountUtils.INSTANCE.findAccounts(userUtils.getUsers()).size() == 0) &&
|
||||
userUtils.getUsers().size() == 0) {
|
||||
|
||||
providersTextView.setText(R.string.nc_get_from_provider);
|
||||
providersTextView.setOnClickListener(view12 -> {
|
||||
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(getResources()
|
||||
.getString(R.string.nc_providers_url)));
|
||||
startActivity(browserIntent);
|
||||
});
|
||||
} else if (AccountUtils.INSTANCE.findAccounts(userUtils.getUsers()).size() > 0) {
|
||||
if (!TextUtils.isEmpty(AccountUtils.INSTANCE.getAppNameBasedOnPackage(getResources()
|
||||
.getString(R.string.nc_import_accounts_from)))) {
|
||||
if (AccountUtils.INSTANCE.findAccounts(userUtils.getUsers()).size() > 1) {
|
||||
providersTextView.setText(String.format(getResources().getString(R.string
|
||||
.nc_server_import_accounts),
|
||||
AccountUtils.INSTANCE.getAppNameBasedOnPackage(getResources()
|
||||
.getString(R.string.nc_import_accounts_from))));
|
||||
} else {
|
||||
providersTextView.setText(String.format(getResources().getString(R.string
|
||||
.nc_server_import_account),
|
||||
AccountUtils.INSTANCE.getAppNameBasedOnPackage(getResources()
|
||||
.getString(R.string.nc_import_accounts_from))));
|
||||
}
|
||||
} else {
|
||||
if (AccountUtils.INSTANCE.findAccounts(userUtils.getUsers()).size() > 1) {
|
||||
providersTextView.setText(
|
||||
getResources().getString(R.string.nc_server_import_accounts_plain));
|
||||
} else {
|
||||
providersTextView.setText(getResources().getString(R.string
|
||||
.nc_server_import_account_plain));
|
||||
}
|
||||
}
|
||||
|
||||
providersTextView.setOnClickListener(view13 -> {
|
||||
Bundle bundle = new Bundle();
|
||||
bundle.putBoolean(BundleKeys.INSTANCE.getKEY_IS_ACCOUNT_IMPORT(), true);
|
||||
getRouter().pushController(RouterTransaction.with(
|
||||
new SwitchAccountController(bundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
});
|
||||
} else {
|
||||
providersTextView.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDestroyView(@NonNull View view) {
|
||||
super.onDestroyView(view);
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_FULL_SENSOR);
|
||||
serverEntry.requestFocus();
|
||||
|
||||
serverEntry.addTextChangedListener(new TextWatcher() {
|
||||
@Override
|
||||
public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterTextChanged(Editable editable) {
|
||||
if (!textFieldBoxes.isOnError() && !TextUtils.isEmpty(serverEntry.getText())) {
|
||||
toggleProceedButton(true);
|
||||
} else {
|
||||
toggleProceedButton(false);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
serverEntry.setOnEditorActionListener((textView, i, keyEvent) -> {
|
||||
if (i == EditorInfo.IME_ACTION_DONE) {
|
||||
checkServerAndProceed();
|
||||
}
|
||||
|
||||
return false;
|
||||
});
|
||||
}
|
||||
|
||||
private void toggleProceedButton(boolean show) {
|
||||
textFieldBoxes.getEndIconImageButton().setEnabled(show);
|
||||
|
||||
if (show) {
|
||||
textFieldBoxes.getEndIconImageButton().setAlpha(1f);
|
||||
} else {
|
||||
textFieldBoxes.getEndIconImageButton().setAlpha(0.5f);
|
||||
}
|
||||
}
|
||||
|
||||
private void checkServerAndProceed() {
|
||||
String url = serverEntry.getText().toString().trim();
|
||||
|
||||
serverEntry.setEnabled(false);
|
||||
progressBar.setVisibility(View.VISIBLE);
|
||||
if (providersTextView.getVisibility() != View.INVISIBLE) {
|
||||
providersTextView.setVisibility(View.INVISIBLE);
|
||||
certTextView.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
|
||||
if (url.endsWith("/")) {
|
||||
url = url.substring(0, url.length() - 1);
|
||||
}
|
||||
|
||||
String queryUrl = url + ApiUtils.getUrlPostfixForStatus();
|
||||
|
||||
if (url.startsWith("http://") || url.startsWith("https://")) {
|
||||
checkServer(queryUrl, false);
|
||||
} else {
|
||||
checkServer("https://" + queryUrl, true);
|
||||
}
|
||||
}
|
||||
|
||||
private void checkServer(String queryUrl, boolean checkForcedHttps) {
|
||||
ncApi.getServerStatus(queryUrl)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(status -> {
|
||||
String productName = getResources().getString(R.string.nc_server_product_name);
|
||||
|
||||
String versionString = status.getVersion().substring(0, status.getVersion().indexOf("."));
|
||||
int version = Integer.parseInt(versionString);
|
||||
if (status.isInstalled() && !status.isMaintenance() &&
|
||||
!status.isNeedsUpgrade() &&
|
||||
version >= 13) {
|
||||
|
||||
getRouter().pushController(RouterTransaction.with(
|
||||
new WebViewLoginController(queryUrl.replace("/status.php", ""),
|
||||
false))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else if (!status.isInstalled()) {
|
||||
textFieldBoxes.setError(String.format(
|
||||
getResources().getString(R.string.nc_server_not_installed), productName),
|
||||
true);
|
||||
toggleProceedButton(false);
|
||||
} else if (status.isNeedsUpgrade()) {
|
||||
textFieldBoxes.setError(String.format(getResources().
|
||||
getString(R.string.nc_server_db_upgrade_needed),
|
||||
productName), true);
|
||||
toggleProceedButton(false);
|
||||
} else if (status.isMaintenance()) {
|
||||
textFieldBoxes.setError(String.format(getResources().
|
||||
getString(R.string.nc_server_maintenance),
|
||||
productName),
|
||||
true);
|
||||
toggleProceedButton(false);
|
||||
} else if (!status.getVersion().startsWith("13.")) {
|
||||
textFieldBoxes.setError(String.format(getResources().
|
||||
getString(R.string.nc_server_version),
|
||||
getResources().getString(R.string.nc_app_name)
|
||||
, productName), true);
|
||||
toggleProceedButton(false);
|
||||
}
|
||||
}, throwable -> {
|
||||
if (checkForcedHttps) {
|
||||
checkServer(queryUrl.replace("https://", "http://"), false);
|
||||
} else {
|
||||
if (throwable.getLocalizedMessage() != null) {
|
||||
textFieldBoxes.setError(throwable.getLocalizedMessage(), true);
|
||||
} else if (throwable.getCause() instanceof CertificateException) {
|
||||
textFieldBoxes.setError(getResources().getString(R.string.nc_certificate_error),
|
||||
false);
|
||||
}
|
||||
|
||||
if (serverEntry != null) {
|
||||
serverEntry.setEnabled(true);
|
||||
}
|
||||
|
||||
progressBar.setVisibility(View.INVISIBLE);
|
||||
if (providersTextView.getVisibility() != View.INVISIBLE) {
|
||||
providersTextView.setVisibility(View.VISIBLE);
|
||||
certTextView.setVisibility(View.VISIBLE);
|
||||
}
|
||||
toggleProceedButton(false);
|
||||
}
|
||||
}, () -> {
|
||||
progressBar.setVisibility(View.INVISIBLE);
|
||||
if (providersTextView.getVisibility() != View.INVISIBLE) {
|
||||
providersTextView.setVisibility(View.VISIBLE);
|
||||
certTextView.setVisibility(View.VISIBLE);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
if (ApplicationWideMessageHolder.getInstance().getMessageType() != null) {
|
||||
if (ApplicationWideMessageHolder.getInstance().getMessageType()
|
||||
.equals(ApplicationWideMessageHolder.MessageType.ACCOUNT_SCHEDULED_FOR_DELETION)) {
|
||||
textFieldBoxes.setError(
|
||||
getResources().getString(R.string.nc_account_scheduled_for_deletion),
|
||||
false);
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(null);
|
||||
} else if (ApplicationWideMessageHolder.getInstance().getMessageType()
|
||||
.equals(ApplicationWideMessageHolder.MessageType.SERVER_WITHOUT_TALK)) {
|
||||
textFieldBoxes.setError(getResources().getString(R.string.nc_settings_no_talk_installed),
|
||||
false);
|
||||
} else if (ApplicationWideMessageHolder.getInstance().getMessageType()
|
||||
.equals(ApplicationWideMessageHolder.MessageType.FAILED_TO_IMPORT_ACCOUNT)) {
|
||||
textFieldBoxes.setError(
|
||||
getResources().getString(R.string.nc_server_failed_to_import_account),
|
||||
false);
|
||||
}
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(null);
|
||||
}
|
||||
|
||||
setCertTextView();
|
||||
}
|
||||
|
||||
private void setCertTextView() {
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> {
|
||||
if (!TextUtils.isEmpty(appPreferences.getTemporaryClientCertAlias())) {
|
||||
certTextView.setText(R.string.nc_change_cert_auth);
|
||||
} else {
|
||||
certTextView.setText(R.string.nc_configure_cert_auth);
|
||||
}
|
||||
|
||||
textFieldBoxes.setError("", true);
|
||||
toggleProceedButton(true);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDestroyView(@NonNull View view) {
|
||||
super.onDestroyView(view);
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_FULL_SENSOR);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -37,13 +37,13 @@ import autodagger.AutoInjector;
|
||||
import butterknife.BindView;
|
||||
import com.bluelinelabs.conductor.RouterTransaction;
|
||||
import com.bluelinelabs.conductor.changehandler.HorizontalChangeHandler;
|
||||
import com.nextcloud.talk.models.ImportAccount;
|
||||
import com.nextcloud.talk.models.json.participants.Participant;
|
||||
import com.nextcloud.talk.R;
|
||||
import com.nextcloud.talk.adapters.items.AdvancedUserItem;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.controllers.base.BaseController;
|
||||
import com.nextcloud.talk.models.ImportAccount;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.models.json.participants.Participant;
|
||||
import com.nextcloud.talk.utils.AccountUtils;
|
||||
import com.nextcloud.talk.utils.bundle.BundleKeys;
|
||||
import com.nextcloud.talk.utils.database.user.UserUtils;
|
||||
@ -61,189 +61,191 @@ import javax.inject.Inject;
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class SwitchAccountController extends BaseController {
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
@BindView(R.id.recyclerView)
|
||||
RecyclerView recyclerView;
|
||||
@BindView(R.id.recyclerView)
|
||||
RecyclerView recyclerView;
|
||||
|
||||
@Inject
|
||||
CookieManager cookieManager;
|
||||
@Inject
|
||||
CookieManager cookieManager;
|
||||
|
||||
@BindView(R.id.swipe_refresh_layout)
|
||||
SwipeRefreshLayout swipeRefreshLayout;
|
||||
private FlexibleAdapter<AbstractFlexibleItem> adapter;
|
||||
private List<AbstractFlexibleItem> userItems = new ArrayList<>();
|
||||
@BindView(R.id.swipe_refresh_layout)
|
||||
SwipeRefreshLayout swipeRefreshLayout;
|
||||
private FlexibleAdapter<AbstractFlexibleItem> adapter;
|
||||
private List<AbstractFlexibleItem> userItems = new ArrayList<>();
|
||||
|
||||
private boolean isAccountImport = false;
|
||||
private boolean isAccountImport = false;
|
||||
|
||||
private FlexibleAdapter.OnItemClickListener onImportItemClickListener = new FlexibleAdapter.OnItemClickListener() {
|
||||
private FlexibleAdapter.OnItemClickListener onImportItemClickListener =
|
||||
new FlexibleAdapter.OnItemClickListener() {
|
||||
@Override
|
||||
public boolean onItemClick(View view, int position) {
|
||||
if (userItems.size() > position) {
|
||||
Account account = ((AdvancedUserItem) userItems.get(position)).getAccount();
|
||||
reauthorizeFromImport(account);
|
||||
}
|
||||
if (userItems.size() > position) {
|
||||
Account account = ((AdvancedUserItem) userItems.get(position)).getAccount();
|
||||
reauthorizeFromImport(account);
|
||||
}
|
||||
|
||||
return true;
|
||||
return true;
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
private FlexibleAdapter.OnItemClickListener onSwitchItemClickListener = new FlexibleAdapter.OnItemClickListener() {
|
||||
private FlexibleAdapter.OnItemClickListener onSwitchItemClickListener =
|
||||
new FlexibleAdapter.OnItemClickListener() {
|
||||
@Override
|
||||
public boolean onItemClick(View view, int position) {
|
||||
if (userItems.size() > position) {
|
||||
UserEntity userEntity = ((AdvancedUserItem) userItems.get(position)).getEntity();
|
||||
userUtils.createOrUpdateUser(null,
|
||||
null, null, null,
|
||||
null, true, null, userEntity.getId(), null, null, null)
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<UserEntity>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
if (userItems.size() > position) {
|
||||
UserEntity userEntity = ((AdvancedUserItem) userItems.get(position)).getEntity();
|
||||
userUtils.createOrUpdateUser(null,
|
||||
null, null, null,
|
||||
null, true, null, userEntity.getId(), null, null, null)
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(new Observer<UserEntity>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(UserEntity userEntity) {
|
||||
cookieManager.getCookieStore().removeAll();
|
||||
@Override
|
||||
public void onNext(UserEntity userEntity) {
|
||||
cookieManager.getCookieStore().removeAll();
|
||||
|
||||
userUtils.disableAllUsersWithoutId(userEntity.getId());
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> getRouter().popCurrentController());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
public SwitchAccountController() {
|
||||
setHasOptionsMenu(true);
|
||||
}
|
||||
|
||||
public SwitchAccountController(Bundle args) {
|
||||
super();
|
||||
setHasOptionsMenu(true);
|
||||
|
||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_IS_ACCOUNT_IMPORT())) {
|
||||
isAccountImport = true;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onOptionsItemSelected(@NonNull MenuItem item) {
|
||||
switch (item.getItemId()) {
|
||||
case android.R.id.home:
|
||||
getRouter().popCurrentController();
|
||||
return true;
|
||||
default:
|
||||
return super.onOptionsItemSelected(item);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_generic_rv, container, false);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
swipeRefreshLayout.setEnabled(false);
|
||||
|
||||
if (getActionBar() != null) {
|
||||
getActionBar().show();
|
||||
}
|
||||
|
||||
if (adapter == null) {
|
||||
adapter = new FlexibleAdapter<>(userItems, getActivity(), false);
|
||||
|
||||
UserEntity userEntity;
|
||||
Participant participant;
|
||||
|
||||
if (!isAccountImport) {
|
||||
for (Object userEntityObject : userUtils.getUsers()) {
|
||||
userEntity = (UserEntity) userEntityObject;
|
||||
if (!userEntity.getCurrent()) {
|
||||
participant = new Participant();
|
||||
participant.setName(userEntity.getDisplayName());
|
||||
|
||||
String userId;
|
||||
|
||||
if (userEntity.getUserId() != null) {
|
||||
userId = userEntity.getUserId();
|
||||
} else {
|
||||
userId = userEntity.getUsername();
|
||||
}
|
||||
participant.setUserId(userId);
|
||||
userItems.add(new AdvancedUserItem(participant, userEntity, null));
|
||||
userUtils.disableAllUsersWithoutId(userEntity.getId());
|
||||
if (getActivity() != null) {
|
||||
getActivity().runOnUiThread(() -> getRouter().popCurrentController());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
adapter.addListener(onSwitchItemClickListener);
|
||||
adapter.updateDataSet(userItems, false);
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
public SwitchAccountController() {
|
||||
setHasOptionsMenu(true);
|
||||
}
|
||||
|
||||
public SwitchAccountController(Bundle args) {
|
||||
super();
|
||||
setHasOptionsMenu(true);
|
||||
|
||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_IS_ACCOUNT_IMPORT())) {
|
||||
isAccountImport = true;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onOptionsItemSelected(@NonNull MenuItem item) {
|
||||
switch (item.getItemId()) {
|
||||
case android.R.id.home:
|
||||
getRouter().popCurrentController();
|
||||
return true;
|
||||
default:
|
||||
return super.onOptionsItemSelected(item);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_generic_rv, container, false);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
swipeRefreshLayout.setEnabled(false);
|
||||
|
||||
if (getActionBar() != null) {
|
||||
getActionBar().show();
|
||||
}
|
||||
|
||||
if (adapter == null) {
|
||||
adapter = new FlexibleAdapter<>(userItems, getActivity(), false);
|
||||
|
||||
UserEntity userEntity;
|
||||
Participant participant;
|
||||
|
||||
if (!isAccountImport) {
|
||||
for (Object userEntityObject : userUtils.getUsers()) {
|
||||
userEntity = (UserEntity) userEntityObject;
|
||||
if (!userEntity.getCurrent()) {
|
||||
participant = new Participant();
|
||||
participant.setName(userEntity.getDisplayName());
|
||||
|
||||
String userId;
|
||||
|
||||
if (userEntity.getUserId() != null) {
|
||||
userId = userEntity.getUserId();
|
||||
} else {
|
||||
Account account;
|
||||
ImportAccount importAccount;
|
||||
for (Object accountObject : AccountUtils.INSTANCE.findAccounts(userUtils.getUsers())) {
|
||||
account = (Account) accountObject;
|
||||
importAccount = AccountUtils.INSTANCE.getInformationFromAccount(account);
|
||||
|
||||
participant = new Participant();
|
||||
participant.setName(importAccount.getUsername());
|
||||
participant.setUserId(importAccount.getUsername());
|
||||
userEntity = new UserEntity();
|
||||
userEntity.setBaseUrl(importAccount.getBaseUrl());
|
||||
userItems.add(new AdvancedUserItem(participant, userEntity, account));
|
||||
}
|
||||
|
||||
adapter.addListener(onImportItemClickListener);
|
||||
adapter.updateDataSet(userItems, false);
|
||||
userId = userEntity.getUsername();
|
||||
}
|
||||
|
||||
participant.setUserId(userId);
|
||||
userItems.add(new AdvancedUserItem(participant, userEntity, null));
|
||||
}
|
||||
}
|
||||
|
||||
prepareViews();
|
||||
adapter.addListener(onSwitchItemClickListener);
|
||||
adapter.updateDataSet(userItems, false);
|
||||
} else {
|
||||
Account account;
|
||||
ImportAccount importAccount;
|
||||
for (Object accountObject : AccountUtils.INSTANCE.findAccounts(userUtils.getUsers())) {
|
||||
account = (Account) accountObject;
|
||||
importAccount = AccountUtils.INSTANCE.getInformationFromAccount(account);
|
||||
|
||||
participant = new Participant();
|
||||
participant.setName(importAccount.getUsername());
|
||||
participant.setUserId(importAccount.getUsername());
|
||||
userEntity = new UserEntity();
|
||||
userEntity.setBaseUrl(importAccount.getBaseUrl());
|
||||
userItems.add(new AdvancedUserItem(participant, userEntity, account));
|
||||
}
|
||||
|
||||
adapter.addListener(onImportItemClickListener);
|
||||
adapter.updateDataSet(userItems, false);
|
||||
}
|
||||
}
|
||||
|
||||
prepareViews();
|
||||
}
|
||||
|
||||
private void prepareViews() {
|
||||
LinearLayoutManager layoutManager = new SmoothScrollLinearLayoutManager(getActivity());
|
||||
recyclerView.setLayoutManager(layoutManager);
|
||||
recyclerView.setHasFixedSize(true);
|
||||
recyclerView.setAdapter(adapter);
|
||||
private void prepareViews() {
|
||||
LinearLayoutManager layoutManager = new SmoothScrollLinearLayoutManager(getActivity());
|
||||
recyclerView.setLayoutManager(layoutManager);
|
||||
recyclerView.setHasFixedSize(true);
|
||||
recyclerView.setAdapter(adapter);
|
||||
|
||||
swipeRefreshLayout.setEnabled(false);
|
||||
}
|
||||
swipeRefreshLayout.setEnabled(false);
|
||||
}
|
||||
|
||||
private void reauthorizeFromImport(Account account) {
|
||||
ImportAccount importAccount = AccountUtils.INSTANCE.getInformationFromAccount(account);
|
||||
Bundle bundle = new Bundle();
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_BASE_URL(), importAccount.getBaseUrl());
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_USERNAME(), importAccount.getUsername());
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_TOKEN(), importAccount.getToken());
|
||||
bundle.putBoolean(BundleKeys.INSTANCE.getKEY_IS_ACCOUNT_IMPORT(), true);
|
||||
getRouter().pushController(RouterTransaction.with(new AccountVerificationController(bundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
}
|
||||
private void reauthorizeFromImport(Account account) {
|
||||
ImportAccount importAccount = AccountUtils.INSTANCE.getInformationFromAccount(account);
|
||||
Bundle bundle = new Bundle();
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_BASE_URL(), importAccount.getBaseUrl());
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_USERNAME(), importAccount.getUsername());
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_TOKEN(), importAccount.getToken());
|
||||
bundle.putBoolean(BundleKeys.INSTANCE.getKEY_IS_ACCOUNT_IMPORT(), true);
|
||||
getRouter().pushController(RouterTransaction.with(new AccountVerificationController(bundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getTitle() {
|
||||
return getResources().getString(R.string.nc_select_an_account);
|
||||
}
|
||||
@Override
|
||||
public String getTitle() {
|
||||
return getResources().getString(R.string.nc_select_an_account);
|
||||
}
|
||||
}
|
||||
|
@ -50,12 +50,12 @@ import autodagger.AutoInjector;
|
||||
import butterknife.BindView;
|
||||
import com.bluelinelabs.conductor.RouterTransaction;
|
||||
import com.bluelinelabs.conductor.changehandler.HorizontalChangeHandler;
|
||||
import com.nextcloud.talk.models.LoginData;
|
||||
import com.nextcloud.talk.R;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.controllers.base.BaseController;
|
||||
import com.nextcloud.talk.events.CertificateEvent;
|
||||
import com.nextcloud.talk.jobs.PushRegistrationWorker;
|
||||
import com.nextcloud.talk.models.LoginData;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.utils.bundle.BundleKeys;
|
||||
import com.nextcloud.talk.utils.database.user.UserUtils;
|
||||
@ -84,388 +84,400 @@ import org.greenrobot.eventbus.EventBus;
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class WebViewLoginController extends BaseController {
|
||||
|
||||
public static final String TAG = "WebViewLoginController";
|
||||
public static final String TAG = "WebViewLoginController";
|
||||
|
||||
private final String PROTOCOL_SUFFIX = "://";
|
||||
private final String LOGIN_URL_DATA_KEY_VALUE_SEPARATOR = ":";
|
||||
private final String PROTOCOL_SUFFIX = "://";
|
||||
private final String LOGIN_URL_DATA_KEY_VALUE_SEPARATOR = ":";
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
@Inject
|
||||
ReactiveEntityStore<Persistable> dataStore;
|
||||
@Inject
|
||||
MagicTrustManager magicTrustManager;
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
@Inject
|
||||
CookieManager cookieManager;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
AppPreferences appPreferences;
|
||||
@Inject
|
||||
ReactiveEntityStore<Persistable> dataStore;
|
||||
@Inject
|
||||
MagicTrustManager magicTrustManager;
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
@Inject
|
||||
CookieManager cookieManager;
|
||||
|
||||
@BindView(R.id.webview)
|
||||
WebView webView;
|
||||
|
||||
@BindView(R.id.webview)
|
||||
WebView webView;
|
||||
@BindView(R.id.progress_bar)
|
||||
ProgressBar progressBar;
|
||||
|
||||
@BindView(R.id.progress_bar)
|
||||
ProgressBar progressBar;
|
||||
private String assembledPrefix;
|
||||
|
||||
private String assembledPrefix;
|
||||
private Disposable userQueryDisposable;
|
||||
|
||||
private Disposable userQueryDisposable;
|
||||
private String baseUrl;
|
||||
private boolean isPasswordUpdate;
|
||||
|
||||
private String baseUrl;
|
||||
private boolean isPasswordUpdate;
|
||||
private String username;
|
||||
private String password;
|
||||
private int loginStep = 0;
|
||||
|
||||
private String username;
|
||||
private String password;
|
||||
private int loginStep = 0;
|
||||
private boolean automatedLoginAttempted = false;
|
||||
|
||||
private boolean automatedLoginAttempted = false;
|
||||
private WebViewFidoBridge webViewFidoBridge;
|
||||
|
||||
private WebViewFidoBridge webViewFidoBridge;
|
||||
public WebViewLoginController(String baseUrl, boolean isPasswordUpdate) {
|
||||
this.baseUrl = baseUrl;
|
||||
this.isPasswordUpdate = isPasswordUpdate;
|
||||
}
|
||||
|
||||
public WebViewLoginController(String baseUrl, boolean isPasswordUpdate) {
|
||||
this.baseUrl = baseUrl;
|
||||
this.isPasswordUpdate = isPasswordUpdate;
|
||||
public WebViewLoginController(String baseUrl, boolean isPasswordUpdate, String username,
|
||||
String password) {
|
||||
this.baseUrl = baseUrl;
|
||||
this.isPasswordUpdate = isPasswordUpdate;
|
||||
this.username = username;
|
||||
this.password = password;
|
||||
}
|
||||
|
||||
private String getWebLoginUserAgent() {
|
||||
return Build.MANUFACTURER.substring(0, 1).toUpperCase(Locale.getDefault()) +
|
||||
Build.MANUFACTURER.substring(1).toLowerCase(Locale.getDefault()) + " " + Build.MODEL + " ("
|
||||
+ getResources().getString(R.string.nc_app_name) + ")";
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_web_view_login, container, false);
|
||||
}
|
||||
|
||||
@SuppressLint("SetJavaScriptEnabled")
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
|
||||
}
|
||||
|
||||
public WebViewLoginController(String baseUrl, boolean isPasswordUpdate, String username, String password) {
|
||||
this.baseUrl = baseUrl;
|
||||
this.isPasswordUpdate = isPasswordUpdate;
|
||||
this.username = username;
|
||||
this.password = password;
|
||||
if (getActionBar() != null) {
|
||||
getActionBar().hide();
|
||||
}
|
||||
|
||||
private String getWebLoginUserAgent() {
|
||||
return Build.MANUFACTURER.substring(0, 1).toUpperCase(Locale.getDefault()) +
|
||||
Build.MANUFACTURER.substring(1).toLowerCase(Locale.getDefault()) + " " + Build.MODEL + " ("
|
||||
+ getResources().getString(R.string.nc_app_name) + ")";
|
||||
}
|
||||
assembledPrefix =
|
||||
getResources().getString(R.string.nc_talk_login_scheme) + PROTOCOL_SUFFIX + "login/";
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_web_view_login, container, false);
|
||||
}
|
||||
webView.getSettings().setAllowFileAccess(false);
|
||||
webView.getSettings().setAllowFileAccessFromFileURLs(false);
|
||||
webView.getSettings().setJavaScriptEnabled(true);
|
||||
webView.getSettings().setJavaScriptCanOpenWindowsAutomatically(false);
|
||||
webView.getSettings().setDomStorageEnabled(true);
|
||||
webView.getSettings().setUserAgentString(getWebLoginUserAgent());
|
||||
webView.getSettings().setSaveFormData(false);
|
||||
webView.getSettings().setSavePassword(false);
|
||||
webView.getSettings().setRenderPriority(WebSettings.RenderPriority.HIGH);
|
||||
webView.clearCache(true);
|
||||
webView.clearFormData();
|
||||
webView.clearHistory();
|
||||
WebView.clearClientCertPreferences(null);
|
||||
|
||||
@SuppressLint("SetJavaScriptEnabled")
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
webViewFidoBridge =
|
||||
WebViewFidoBridge.createInstanceForWebView((AppCompatActivity) getActivity(), webView);
|
||||
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
|
||||
CookieSyncManager.createInstance(getActivity());
|
||||
android.webkit.CookieManager.getInstance().removeAllCookies(null);
|
||||
|
||||
Map<String, String> headers = new HashMap<>();
|
||||
headers.put("OCS-APIRequest", "true");
|
||||
|
||||
webView.setWebViewClient(new WebViewClient() {
|
||||
private boolean basePageLoaded;
|
||||
|
||||
@Override
|
||||
public WebResourceResponse shouldInterceptRequest(WebView view, WebResourceRequest request) {
|
||||
webViewFidoBridge.delegateShouldInterceptRequest(view, request);
|
||||
return super.shouldInterceptRequest(view, request);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPageStarted(WebView view, String url, Bitmap favicon) {
|
||||
super.onPageStarted(view, url, favicon);
|
||||
webViewFidoBridge.delegateOnPageStarted(view, url, favicon);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean shouldOverrideUrlLoading(WebView view, String url) {
|
||||
if (url.startsWith(assembledPrefix)) {
|
||||
parseAndLoginFromWebView(url);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPageFinished(WebView view, String url) {
|
||||
loginStep++;
|
||||
|
||||
if (!basePageLoaded) {
|
||||
if (progressBar != null) {
|
||||
progressBar.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
if (webView != null) {
|
||||
webView.setVisibility(View.VISIBLE);
|
||||
}
|
||||
basePageLoaded = true;
|
||||
}
|
||||
|
||||
if (getActionBar() != null) {
|
||||
getActionBar().hide();
|
||||
}
|
||||
|
||||
assembledPrefix = getResources().getString(R.string.nc_talk_login_scheme) + PROTOCOL_SUFFIX + "login/";
|
||||
|
||||
webView.getSettings().setAllowFileAccess(false);
|
||||
webView.getSettings().setAllowFileAccessFromFileURLs(false);
|
||||
webView.getSettings().setJavaScriptEnabled(true);
|
||||
webView.getSettings().setJavaScriptCanOpenWindowsAutomatically(false);
|
||||
webView.getSettings().setDomStorageEnabled(true);
|
||||
webView.getSettings().setUserAgentString(getWebLoginUserAgent());
|
||||
webView.getSettings().setSaveFormData(false);
|
||||
webView.getSettings().setSavePassword(false);
|
||||
webView.getSettings().setRenderPriority(WebSettings.RenderPriority.HIGH);
|
||||
webView.clearCache(true);
|
||||
webView.clearFormData();
|
||||
webView.clearHistory();
|
||||
WebView.clearClientCertPreferences(null);
|
||||
|
||||
webViewFidoBridge = WebViewFidoBridge.createInstanceForWebView((AppCompatActivity) getActivity(), webView);
|
||||
|
||||
CookieSyncManager.createInstance(getActivity());
|
||||
android.webkit.CookieManager.getInstance().removeAllCookies(null);
|
||||
|
||||
Map<String, String> headers = new HashMap<>();
|
||||
headers.put("OCS-APIRequest", "true");
|
||||
|
||||
webView.setWebViewClient(new WebViewClient() {
|
||||
private boolean basePageLoaded;
|
||||
|
||||
@Override
|
||||
public WebResourceResponse shouldInterceptRequest(WebView view, WebResourceRequest request) {
|
||||
webViewFidoBridge.delegateShouldInterceptRequest(view, request);
|
||||
return super.shouldInterceptRequest(view, request);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPageStarted(WebView view, String url, Bitmap favicon) {
|
||||
super.onPageStarted(view, url, favicon);
|
||||
webViewFidoBridge.delegateOnPageStarted(view, url, favicon);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean shouldOverrideUrlLoading(WebView view, String url) {
|
||||
if (url.startsWith(assembledPrefix)) {
|
||||
parseAndLoginFromWebView(url);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onPageFinished(WebView view, String url) {
|
||||
loginStep++;
|
||||
|
||||
if (!basePageLoaded) {
|
||||
if (progressBar != null) {
|
||||
progressBar.setVisibility(View.GONE);
|
||||
}
|
||||
|
||||
if (webView != null) {
|
||||
webView.setVisibility(View.VISIBLE);
|
||||
}
|
||||
basePageLoaded = true;
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(username) && webView != null) {
|
||||
if (loginStep == 1) {
|
||||
webView.loadUrl("javascript: {document.getElementsByClassName('login')[0].click(); };");
|
||||
} else if (!automatedLoginAttempted) {
|
||||
automatedLoginAttempted = true;
|
||||
if (TextUtils.isEmpty(password)) {
|
||||
webView.loadUrl("javascript:var justStore = document.getElementById('user').value = '" + username + "';");
|
||||
} else {
|
||||
webView.loadUrl("javascript: {" +
|
||||
"document.getElementById('user').value = '" + username + "';" +
|
||||
"document.getElementById('password').value = '" + password + "';" +
|
||||
"document.getElementById('submit').click(); };");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
super.onPageFinished(view, url);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onReceivedClientCertRequest(WebView view, ClientCertRequest request) {
|
||||
UserEntity userEntity = userUtils.getCurrentUser();
|
||||
|
||||
String alias = null;
|
||||
if (!isPasswordUpdate) {
|
||||
alias = appPreferences.getTemporaryClientCertAlias();
|
||||
}
|
||||
|
||||
if (TextUtils.isEmpty(alias) && (userEntity != null)) {
|
||||
alias = userEntity.getClientCertificate();
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(alias)) {
|
||||
String finalAlias = alias;
|
||||
new Thread(() -> {
|
||||
try {
|
||||
PrivateKey privateKey = KeyChain.getPrivateKey(getActivity(), finalAlias);
|
||||
X509Certificate[] certificates = KeyChain.getCertificateChain(getActivity(), finalAlias);
|
||||
if (privateKey != null && certificates != null) {
|
||||
request.proceed(privateKey, certificates);
|
||||
} else {
|
||||
request.cancel();
|
||||
}
|
||||
} catch (KeyChainException | InterruptedException e) {
|
||||
request.cancel();
|
||||
}
|
||||
}).start();
|
||||
} else {
|
||||
KeyChain.choosePrivateKeyAlias(getActivity(), chosenAlias -> {
|
||||
if (chosenAlias != null) {
|
||||
appPreferences.setTemporaryClientCertAlias(chosenAlias);
|
||||
new Thread(() -> {
|
||||
PrivateKey privateKey = null;
|
||||
try {
|
||||
privateKey = KeyChain.getPrivateKey(getActivity(), chosenAlias);
|
||||
X509Certificate[] certificates = KeyChain.getCertificateChain(getActivity(), chosenAlias);
|
||||
if (privateKey != null && certificates != null) {
|
||||
request.proceed(privateKey, certificates);
|
||||
} else {
|
||||
request.cancel();
|
||||
}
|
||||
} catch (KeyChainException | InterruptedException e) {
|
||||
request.cancel();
|
||||
}
|
||||
}).start();
|
||||
} else {
|
||||
request.cancel();
|
||||
}
|
||||
}, new String[]{"RSA", "EC"}, null, request.getHost(), request.getPort(), null);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) {
|
||||
try {
|
||||
SslCertificate sslCertificate = error.getCertificate();
|
||||
Field f = sslCertificate.getClass().getDeclaredField("mX509Certificate");
|
||||
f.setAccessible(true);
|
||||
X509Certificate cert = (X509Certificate) f.get(sslCertificate);
|
||||
|
||||
if (cert == null) {
|
||||
handler.cancel();
|
||||
} else {
|
||||
try {
|
||||
magicTrustManager.checkServerTrusted(new X509Certificate[]{cert}, "generic");
|
||||
handler.proceed();
|
||||
} catch (CertificateException exception) {
|
||||
eventBus.post(new CertificateEvent(cert, magicTrustManager, handler));
|
||||
}
|
||||
}
|
||||
} catch (Exception exception) {
|
||||
handler.cancel();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onReceivedError(WebView view, int errorCode, String description, String failingUrl) {
|
||||
super.onReceivedError(view, errorCode, description, failingUrl);
|
||||
}
|
||||
});
|
||||
|
||||
webView.loadUrl(baseUrl + "/index.php/login/flow", headers);
|
||||
}
|
||||
|
||||
private void dispose() {
|
||||
if (userQueryDisposable != null && !userQueryDisposable.isDisposed()) {
|
||||
userQueryDisposable.dispose();
|
||||
}
|
||||
|
||||
userQueryDisposable = null;
|
||||
}
|
||||
|
||||
private void parseAndLoginFromWebView(String dataString) {
|
||||
LoginData loginData = parseLoginData(assembledPrefix, dataString);
|
||||
|
||||
if (loginData != null) {
|
||||
dispose();
|
||||
|
||||
UserEntity currentUser = userUtils.getCurrentUser();
|
||||
|
||||
ApplicationWideMessageHolder.MessageType messageType = null;
|
||||
|
||||
if (!isPasswordUpdate && userUtils.getIfUserWithUsernameAndServer(loginData.getUsername(), baseUrl)) {
|
||||
messageType = ApplicationWideMessageHolder.MessageType.ACCOUNT_UPDATED_NOT_ADDED;
|
||||
}
|
||||
|
||||
if (userUtils.checkIfUserIsScheduledForDeletion(loginData.getUsername(), baseUrl)) {
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(
|
||||
ApplicationWideMessageHolder.MessageType.ACCOUNT_SCHEDULED_FOR_DELETION);
|
||||
|
||||
if (!isPasswordUpdate) {
|
||||
getRouter().popToRoot();
|
||||
} else {
|
||||
getRouter().popCurrentController();
|
||||
}
|
||||
}
|
||||
|
||||
ApplicationWideMessageHolder.MessageType finalMessageType = messageType;
|
||||
cookieManager.getCookieStore().removeAll();
|
||||
|
||||
if (!isPasswordUpdate && finalMessageType == null) {
|
||||
Bundle bundle = new Bundle();
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_USERNAME(), loginData.getUsername());
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_TOKEN(), loginData.getToken());
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_BASE_URL(), loginData.getServerUrl());
|
||||
String protocol = "";
|
||||
|
||||
if (baseUrl.startsWith("http://")) {
|
||||
protocol = "http://";
|
||||
} else if (baseUrl.startsWith("https://")) {
|
||||
protocol = "https://";
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(protocol)) {
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_ORIGINAL_PROTOCOL(), protocol);
|
||||
}
|
||||
|
||||
getRouter().pushController(RouterTransaction.with(new AccountVerificationController
|
||||
(bundle)).pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
if (!TextUtils.isEmpty(username) && webView != null) {
|
||||
if (loginStep == 1) {
|
||||
webView.loadUrl("javascript: {document.getElementsByClassName('login')[0].click(); };");
|
||||
} else if (!automatedLoginAttempted) {
|
||||
automatedLoginAttempted = true;
|
||||
if (TextUtils.isEmpty(password)) {
|
||||
webView.loadUrl("javascript:var justStore = document.getElementById('user').value = '"
|
||||
+ username
|
||||
+ "';");
|
||||
} else {
|
||||
if (isPasswordUpdate) {
|
||||
if (currentUser != null) {
|
||||
userQueryDisposable = userUtils.createOrUpdateUser(null, loginData.getToken(),
|
||||
null, null, "", true,
|
||||
null, currentUser.getId(), null, appPreferences.getTemporaryClientCertAlias(), null)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(userEntity -> {
|
||||
if (finalMessageType != null) {
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(finalMessageType);
|
||||
}
|
||||
|
||||
OneTimeWorkRequest pushRegistrationWork = new OneTimeWorkRequest.Builder(PushRegistrationWorker.class).build();
|
||||
WorkManager.getInstance().enqueue(pushRegistrationWork);
|
||||
|
||||
getRouter().popCurrentController();
|
||||
}, throwable -> dispose(),
|
||||
this::dispose);
|
||||
}
|
||||
} else {
|
||||
if (finalMessageType != null) {
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(finalMessageType);
|
||||
}
|
||||
getRouter().popToRoot();
|
||||
|
||||
}
|
||||
webView.loadUrl("javascript: {" +
|
||||
"document.getElementById('user').value = '" + username + "';" +
|
||||
"document.getElementById('password').value = '" + password + "';" +
|
||||
"document.getElementById('submit').click(); };");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private LoginData parseLoginData(String prefix, String dataString) {
|
||||
if (dataString.length() < prefix.length()) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
LoginData loginData = new LoginData();
|
||||
super.onPageFinished(view, url);
|
||||
}
|
||||
|
||||
// format is xxx://login/server:xxx&user:xxx&password:xxx
|
||||
String data = dataString.substring(prefix.length());
|
||||
@Override
|
||||
public void onReceivedClientCertRequest(WebView view, ClientCertRequest request) {
|
||||
UserEntity userEntity = userUtils.getCurrentUser();
|
||||
|
||||
String[] values = data.split("&");
|
||||
|
||||
if (values.length != 3) {
|
||||
return null;
|
||||
String alias = null;
|
||||
if (!isPasswordUpdate) {
|
||||
alias = appPreferences.getTemporaryClientCertAlias();
|
||||
}
|
||||
|
||||
for (String value : values) {
|
||||
if (value.startsWith("user" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR)) {
|
||||
loginData.setUsername(URLDecoder.decode(
|
||||
value.substring(("user" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR).length())));
|
||||
} else if (value.startsWith("password" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR)) {
|
||||
loginData.setToken(URLDecoder.decode(
|
||||
value.substring(("password" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR).length())));
|
||||
} else if (value.startsWith("server" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR)) {
|
||||
loginData.setServerUrl(URLDecoder.decode(
|
||||
value.substring(("server" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR).length())));
|
||||
} else {
|
||||
return null;
|
||||
if (TextUtils.isEmpty(alias) && (userEntity != null)) {
|
||||
alias = userEntity.getClientCertificate();
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(alias)) {
|
||||
String finalAlias = alias;
|
||||
new Thread(() -> {
|
||||
try {
|
||||
PrivateKey privateKey = KeyChain.getPrivateKey(getActivity(), finalAlias);
|
||||
X509Certificate[] certificates =
|
||||
KeyChain.getCertificateChain(getActivity(), finalAlias);
|
||||
if (privateKey != null && certificates != null) {
|
||||
request.proceed(privateKey, certificates);
|
||||
} else {
|
||||
request.cancel();
|
||||
}
|
||||
} catch (KeyChainException | InterruptedException e) {
|
||||
request.cancel();
|
||||
}
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(loginData.getServerUrl()) && !TextUtils.isEmpty(loginData.getUsername()) &&
|
||||
!TextUtils.isEmpty(loginData.getToken())) {
|
||||
return loginData;
|
||||
}).start();
|
||||
} else {
|
||||
return null;
|
||||
KeyChain.choosePrivateKeyAlias(getActivity(), chosenAlias -> {
|
||||
if (chosenAlias != null) {
|
||||
appPreferences.setTemporaryClientCertAlias(chosenAlias);
|
||||
new Thread(() -> {
|
||||
PrivateKey privateKey = null;
|
||||
try {
|
||||
privateKey = KeyChain.getPrivateKey(getActivity(), chosenAlias);
|
||||
X509Certificate[] certificates =
|
||||
KeyChain.getCertificateChain(getActivity(), chosenAlias);
|
||||
if (privateKey != null && certificates != null) {
|
||||
request.proceed(privateKey, certificates);
|
||||
} else {
|
||||
request.cancel();
|
||||
}
|
||||
} catch (KeyChainException | InterruptedException e) {
|
||||
request.cancel();
|
||||
}
|
||||
}).start();
|
||||
} else {
|
||||
request.cancel();
|
||||
}
|
||||
}, new String[] { "RSA", "EC" }, null, request.getHost(), request.getPort(), null);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) {
|
||||
try {
|
||||
SslCertificate sslCertificate = error.getCertificate();
|
||||
Field f = sslCertificate.getClass().getDeclaredField("mX509Certificate");
|
||||
f.setAccessible(true);
|
||||
X509Certificate cert = (X509Certificate) f.get(sslCertificate);
|
||||
|
||||
if (cert == null) {
|
||||
handler.cancel();
|
||||
} else {
|
||||
try {
|
||||
magicTrustManager.checkServerTrusted(new X509Certificate[] { cert }, "generic");
|
||||
handler.proceed();
|
||||
} catch (CertificateException exception) {
|
||||
eventBus.post(new CertificateEvent(cert, magicTrustManager, handler));
|
||||
}
|
||||
}
|
||||
} catch (Exception exception) {
|
||||
handler.cancel();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onReceivedError(WebView view, int errorCode, String description,
|
||||
String failingUrl) {
|
||||
super.onReceivedError(view, errorCode, description, failingUrl);
|
||||
}
|
||||
});
|
||||
|
||||
webView.loadUrl(baseUrl + "/index.php/login/flow", headers);
|
||||
}
|
||||
|
||||
private void dispose() {
|
||||
if (userQueryDisposable != null && !userQueryDisposable.isDisposed()) {
|
||||
userQueryDisposable.dispose();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
super.onDestroy();
|
||||
dispose();
|
||||
userQueryDisposable = null;
|
||||
}
|
||||
|
||||
private void parseAndLoginFromWebView(String dataString) {
|
||||
LoginData loginData = parseLoginData(assembledPrefix, dataString);
|
||||
|
||||
if (loginData != null) {
|
||||
dispose();
|
||||
|
||||
UserEntity currentUser = userUtils.getCurrentUser();
|
||||
|
||||
ApplicationWideMessageHolder.MessageType messageType = null;
|
||||
|
||||
if (!isPasswordUpdate && userUtils.getIfUserWithUsernameAndServer(loginData.getUsername(),
|
||||
baseUrl)) {
|
||||
messageType = ApplicationWideMessageHolder.MessageType.ACCOUNT_UPDATED_NOT_ADDED;
|
||||
}
|
||||
|
||||
if (userUtils.checkIfUserIsScheduledForDeletion(loginData.getUsername(), baseUrl)) {
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(
|
||||
ApplicationWideMessageHolder.MessageType.ACCOUNT_SCHEDULED_FOR_DELETION);
|
||||
|
||||
if (!isPasswordUpdate) {
|
||||
getRouter().popToRoot();
|
||||
} else {
|
||||
getRouter().popCurrentController();
|
||||
}
|
||||
}
|
||||
|
||||
ApplicationWideMessageHolder.MessageType finalMessageType = messageType;
|
||||
cookieManager.getCookieStore().removeAll();
|
||||
|
||||
if (!isPasswordUpdate && finalMessageType == null) {
|
||||
Bundle bundle = new Bundle();
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_USERNAME(), loginData.getUsername());
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_TOKEN(), loginData.getToken());
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_BASE_URL(), loginData.getServerUrl());
|
||||
String protocol = "";
|
||||
|
||||
if (baseUrl.startsWith("http://")) {
|
||||
protocol = "http://";
|
||||
} else if (baseUrl.startsWith("https://")) {
|
||||
protocol = "https://";
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(protocol)) {
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_ORIGINAL_PROTOCOL(), protocol);
|
||||
}
|
||||
|
||||
getRouter().pushController(RouterTransaction.with(new AccountVerificationController
|
||||
(bundle)).pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else {
|
||||
if (isPasswordUpdate) {
|
||||
if (currentUser != null) {
|
||||
userQueryDisposable = userUtils.createOrUpdateUser(null, loginData.getToken(),
|
||||
null, null, "", true,
|
||||
null, currentUser.getId(), null, appPreferences.getTemporaryClientCertAlias(), null)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
.as(AutoDispose.autoDisposable(getScopeProvider()))
|
||||
.subscribe(userEntity -> {
|
||||
if (finalMessageType != null) {
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(finalMessageType);
|
||||
}
|
||||
|
||||
OneTimeWorkRequest pushRegistrationWork =
|
||||
new OneTimeWorkRequest.Builder(PushRegistrationWorker.class).build();
|
||||
WorkManager.getInstance().enqueue(pushRegistrationWork);
|
||||
|
||||
getRouter().popCurrentController();
|
||||
}, throwable -> dispose(),
|
||||
this::dispose);
|
||||
}
|
||||
} else {
|
||||
if (finalMessageType != null) {
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(finalMessageType);
|
||||
}
|
||||
getRouter().popToRoot();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private LoginData parseLoginData(String prefix, String dataString) {
|
||||
if (dataString.length() < prefix.length()) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDestroyView(@NonNull View view) {
|
||||
super.onDestroyView(view);
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_FULL_SENSOR);
|
||||
}
|
||||
LoginData loginData = new LoginData();
|
||||
|
||||
// format is xxx://login/server:xxx&user:xxx&password:xxx
|
||||
String data = dataString.substring(prefix.length());
|
||||
|
||||
String[] values = data.split("&");
|
||||
|
||||
if (values.length != 3) {
|
||||
return null;
|
||||
}
|
||||
|
||||
for (String value : values) {
|
||||
if (value.startsWith("user" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR)) {
|
||||
loginData.setUsername(URLDecoder.decode(
|
||||
value.substring(("user" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR).length())));
|
||||
} else if (value.startsWith("password" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR)) {
|
||||
loginData.setToken(URLDecoder.decode(
|
||||
value.substring(("password" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR).length())));
|
||||
} else if (value.startsWith("server" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR)) {
|
||||
loginData.setServerUrl(URLDecoder.decode(
|
||||
value.substring(("server" + LOGIN_URL_DATA_KEY_VALUE_SEPARATOR).length())));
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(loginData.getServerUrl())
|
||||
&& !TextUtils.isEmpty(loginData.getUsername())
|
||||
&&
|
||||
!TextUtils.isEmpty(loginData.getToken())) {
|
||||
return loginData;
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
super.onDestroy();
|
||||
dispose();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDestroyView(@NonNull View view) {
|
||||
super.onDestroyView(view);
|
||||
if (getActivity() != null) {
|
||||
getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_FULL_SENSOR);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -31,27 +31,33 @@ import com.bluelinelabs.conductor.Controller
|
||||
|
||||
abstract class ButterKnifeController : Controller {
|
||||
|
||||
protected var unbinder: Unbinder? = null
|
||||
protected var unbinder: Unbinder? = null
|
||||
|
||||
constructor()
|
||||
constructor()
|
||||
|
||||
constructor(args: Bundle) : super(args)
|
||||
|
||||
protected abstract fun inflateView(inflater: LayoutInflater, container: ViewGroup): View
|
||||
protected abstract fun inflateView(
|
||||
inflater: LayoutInflater,
|
||||
container: ViewGroup
|
||||
): View
|
||||
|
||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup): View {
|
||||
val view = inflateView(inflater, container)
|
||||
unbinder = ButterKnife.bind(this, view)
|
||||
onViewBound(view)
|
||||
return view
|
||||
}
|
||||
override fun onCreateView(
|
||||
inflater: LayoutInflater,
|
||||
container: ViewGroup
|
||||
): View {
|
||||
val view = inflateView(inflater, container)
|
||||
unbinder = ButterKnife.bind(this, view)
|
||||
onViewBound(view)
|
||||
return view
|
||||
}
|
||||
|
||||
protected open fun onViewBound(view: View) {}
|
||||
protected open fun onViewBound(view: View) {}
|
||||
|
||||
override fun onDestroyView(view: View) {
|
||||
super.onDestroyView(view)
|
||||
unbinder!!.unbind()
|
||||
unbinder = null
|
||||
}
|
||||
override fun onDestroyView(view: View) {
|
||||
super.onDestroyView(view)
|
||||
unbinder!!.unbind()
|
||||
unbinder = null
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -21,5 +21,5 @@ package com.nextcloud.talk.controllers.base.providers;
|
||||
import androidx.appcompat.app.ActionBar;
|
||||
|
||||
public interface ActionBarProvider {
|
||||
ActionBar getSupportActionBar();
|
||||
ActionBar getSupportActionBar();
|
||||
}
|
||||
|
@ -64,266 +64,279 @@ import org.parceler.Parcels;
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class EntryMenuController extends BaseController {
|
||||
|
||||
@BindView(R.id.ok_button)
|
||||
Button proceedButton;
|
||||
@BindView(R.id.ok_button)
|
||||
Button proceedButton;
|
||||
|
||||
@BindView(R.id.text_edit)
|
||||
EmojiTextInputEditText editText;
|
||||
@BindView(R.id.text_edit)
|
||||
EmojiTextInputEditText editText;
|
||||
|
||||
@BindView(R.id.text_input_layout)
|
||||
TextInputLayout textInputLayout;
|
||||
@BindView(R.id.text_input_layout)
|
||||
TextInputLayout textInputLayout;
|
||||
|
||||
@BindView(R.id.smileyButton)
|
||||
ImageView smileyButton;
|
||||
@BindView(R.id.smileyButton)
|
||||
ImageView smileyButton;
|
||||
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
private int operationCode;
|
||||
private Conversation conversation;
|
||||
private Intent shareIntent;
|
||||
private String packageName;
|
||||
private String name;
|
||||
private String callUrl;
|
||||
private int operationCode;
|
||||
private Conversation conversation;
|
||||
private Intent shareIntent;
|
||||
private String packageName;
|
||||
private String name;
|
||||
private String callUrl;
|
||||
|
||||
private EmojiPopup emojiPopup;
|
||||
private EmojiPopup emojiPopup;
|
||||
|
||||
private Bundle originalBundle;
|
||||
|
||||
private Bundle originalBundle;
|
||||
public EntryMenuController(Bundle args) {
|
||||
super();
|
||||
originalBundle = args;
|
||||
|
||||
public EntryMenuController(Bundle args) {
|
||||
super();
|
||||
originalBundle = args;
|
||||
|
||||
this.operationCode = args.getInt(BundleKeys.INSTANCE.getKEY_OPERATION_CODE());
|
||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_ROOM())) {
|
||||
this.conversation = Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_ROOM()));
|
||||
}
|
||||
|
||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_SHARE_INTENT())) {
|
||||
this.shareIntent = Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_SHARE_INTENT()));
|
||||
}
|
||||
|
||||
this.name = args.getString(BundleKeys.INSTANCE.getKEY_APP_ITEM_NAME(), "");
|
||||
this.packageName = args.getString(BundleKeys.INSTANCE.getKEY_APP_ITEM_PACKAGE_NAME(), "");
|
||||
this.callUrl = args.getString(BundleKeys.INSTANCE.getKEY_CALL_URL(), "");
|
||||
this.operationCode = args.getInt(BundleKeys.INSTANCE.getKEY_OPERATION_CODE());
|
||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_ROOM())) {
|
||||
this.conversation = Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_ROOM()));
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_entry_menu, container, false);
|
||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_SHARE_INTENT())) {
|
||||
this.shareIntent =
|
||||
Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_SHARE_INTENT()));
|
||||
}
|
||||
|
||||
@OnClick(R.id.smileyButton)
|
||||
void onSmileyClick() {
|
||||
emojiPopup.toggle();
|
||||
this.name = args.getString(BundleKeys.INSTANCE.getKEY_APP_ITEM_NAME(), "");
|
||||
this.packageName = args.getString(BundleKeys.INSTANCE.getKEY_APP_ITEM_PACKAGE_NAME(), "");
|
||||
this.callUrl = args.getString(BundleKeys.INSTANCE.getKEY_CALL_URL(), "");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
||||
return inflater.inflate(R.layout.controller_entry_menu, container, false);
|
||||
}
|
||||
|
||||
@OnClick(R.id.smileyButton)
|
||||
void onSmileyClick() {
|
||||
emojiPopup.toggle();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
if (ApplicationWideMessageHolder.getInstance().getMessageType() != null &&
|
||||
ApplicationWideMessageHolder.getInstance()
|
||||
.getMessageType()
|
||||
.equals(ApplicationWideMessageHolder.MessageType.CALL_PASSWORD_WRONG)) {
|
||||
textInputLayout.setError(getResources().getString(R.string.nc_wrong_password));
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(null);
|
||||
if (proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(false);
|
||||
proceedButton.setAlpha(0.7f);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@OnClick(R.id.ok_button)
|
||||
public void onProceedButtonClick() {
|
||||
Bundle bundle;
|
||||
if (operationCode == 99) {
|
||||
eventBus.post(new BottomSheetLockEvent(false, 0, false, false));
|
||||
bundle = new Bundle();
|
||||
bundle.putParcelable(BundleKeys.INSTANCE.getKEY_ROOM(), Parcels.wrap(conversation));
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_CALL_URL(), callUrl);
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_CONVERSATION_PASSWORD(),
|
||||
editText.getText().toString());
|
||||
bundle.putInt(BundleKeys.INSTANCE.getKEY_OPERATION_CODE(), operationCode);
|
||||
if (originalBundle.containsKey(BundleKeys.INSTANCE.getKEY_SERVER_CAPABILITIES())) {
|
||||
bundle.putParcelable(BundleKeys.INSTANCE.getKEY_SERVER_CAPABILITIES(),
|
||||
originalBundle.getParcelable(BundleKeys.INSTANCE.getKEY_SERVER_CAPABILITIES()));
|
||||
}
|
||||
|
||||
getRouter().pushController(RouterTransaction.with(new OperationsMenuController(bundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else if (operationCode != 7 && operationCode != 10 && operationCode != 11) {
|
||||
eventBus.post(new BottomSheetLockEvent(false, 0, false, false));
|
||||
bundle = new Bundle();
|
||||
if (operationCode == 4 || operationCode == 6) {
|
||||
conversation.setPassword(editText.getText().toString());
|
||||
} else {
|
||||
conversation.setName(editText.getText().toString());
|
||||
}
|
||||
bundle.putParcelable(BundleKeys.INSTANCE.getKEY_ROOM(), Parcels.wrap(conversation));
|
||||
bundle.putInt(BundleKeys.INSTANCE.getKEY_OPERATION_CODE(), operationCode);
|
||||
getRouter().pushController(RouterTransaction.with(new OperationsMenuController(bundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else if (operationCode == 7) {
|
||||
if (getActivity() != null) {
|
||||
shareIntent.putExtra(Intent.EXTRA_TEXT, ShareUtils.getStringForIntent(getActivity(),
|
||||
editText.getText().toString(), userUtils, conversation));
|
||||
Intent intent = new Intent(shareIntent);
|
||||
intent.setComponent(new ComponentName(packageName, name));
|
||||
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
getActivity().startActivity(intent);
|
||||
eventBus.post(new BottomSheetLockEvent(true, 0, false, true));
|
||||
}
|
||||
} else if (operationCode != 11) {
|
||||
eventBus.post(new BottomSheetLockEvent(false, 0, false, false));
|
||||
bundle = new Bundle();
|
||||
bundle.putInt(BundleKeys.INSTANCE.getKEY_OPERATION_CODE(), operationCode);
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_CALL_URL(), editText.getText().toString());
|
||||
getRouter().pushController(RouterTransaction.with(new OperationsMenuController(bundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else if (operationCode == 11) {
|
||||
eventBus.post(new BottomSheetLockEvent(false, 0, false, false));
|
||||
originalBundle.putString(BundleKeys.INSTANCE.getKEY_CONVERSATION_NAME(),
|
||||
editText.getText().toString());
|
||||
getRouter().pushController(
|
||||
RouterTransaction.with(new OperationsMenuController(originalBundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
if (conversation != null && operationCode == 2) {
|
||||
editText.setText(conversation.getName());
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onAttach(@NonNull View view) {
|
||||
super.onAttach(view);
|
||||
if (ApplicationWideMessageHolder.getInstance().getMessageType() != null &&
|
||||
ApplicationWideMessageHolder.getInstance().getMessageType().equals(ApplicationWideMessageHolder.MessageType.CALL_PASSWORD_WRONG)) {
|
||||
textInputLayout.setError(getResources().getString(R.string.nc_wrong_password));
|
||||
ApplicationWideMessageHolder.getInstance().setMessageType(null);
|
||||
if (proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(false);
|
||||
proceedButton.setAlpha(0.7f);
|
||||
}
|
||||
}
|
||||
}
|
||||
editText.setOnEditorActionListener((v, actionId, event) -> {
|
||||
if (actionId == EditorInfo.IME_ACTION_DONE
|
||||
&& proceedButton != null
|
||||
&& proceedButton.isEnabled()) {
|
||||
proceedButton.callOnClick();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
});
|
||||
|
||||
@OnClick(R.id.ok_button)
|
||||
public void onProceedButtonClick() {
|
||||
Bundle bundle;
|
||||
if (operationCode == 99) {
|
||||
eventBus.post(new BottomSheetLockEvent(false, 0, false, false));
|
||||
bundle = new Bundle();
|
||||
bundle.putParcelable(BundleKeys.INSTANCE.getKEY_ROOM(), Parcels.wrap(conversation));
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_CALL_URL(), callUrl);
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_CONVERSATION_PASSWORD(), editText.getText().toString());
|
||||
bundle.putInt(BundleKeys.INSTANCE.getKEY_OPERATION_CODE(), operationCode);
|
||||
if (originalBundle.containsKey(BundleKeys.INSTANCE.getKEY_SERVER_CAPABILITIES())) {
|
||||
bundle.putParcelable(BundleKeys.INSTANCE.getKEY_SERVER_CAPABILITIES(), originalBundle.getParcelable(BundleKeys.INSTANCE.getKEY_SERVER_CAPABILITIES()));
|
||||
}
|
||||
editText.addTextChangedListener(new TextWatcher() {
|
||||
@Override
|
||||
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
|
||||
|
||||
getRouter().pushController(RouterTransaction.with(new OperationsMenuController(bundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else if (operationCode != 7 && operationCode != 10 && operationCode != 11) {
|
||||
eventBus.post(new BottomSheetLockEvent(false, 0, false, false));
|
||||
bundle = new Bundle();
|
||||
if (operationCode == 4 || operationCode == 6) {
|
||||
conversation.setPassword(editText.getText().toString());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onTextChanged(CharSequence s, int start, int before, int count) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterTextChanged(Editable s) {
|
||||
if (!TextUtils.isEmpty(s)) {
|
||||
if (operationCode == 2) {
|
||||
if (conversation.getName() == null || !conversation.getName().equals(s.toString())) {
|
||||
if (!proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(true);
|
||||
proceedButton.setAlpha(1.0f);
|
||||
}
|
||||
textInputLayout.setErrorEnabled(false);
|
||||
} else {
|
||||
conversation.setName(editText.getText().toString());
|
||||
if (proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(false);
|
||||
proceedButton.setAlpha(0.38f);
|
||||
}
|
||||
textInputLayout.setError(getResources().getString(R.string.nc_call_name_is_same));
|
||||
}
|
||||
bundle.putParcelable(BundleKeys.INSTANCE.getKEY_ROOM(), Parcels.wrap(conversation));
|
||||
bundle.putInt(BundleKeys.INSTANCE.getKEY_OPERATION_CODE(), operationCode);
|
||||
getRouter().pushController(RouterTransaction.with(new OperationsMenuController(bundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
} else if (operationCode == 7) {
|
||||
if (getActivity() != null) {
|
||||
shareIntent.putExtra(Intent.EXTRA_TEXT, ShareUtils.getStringForIntent(getActivity(),
|
||||
editText.getText().toString(), userUtils, conversation));
|
||||
Intent intent = new Intent(shareIntent);
|
||||
intent.setComponent(new ComponentName(packageName, name));
|
||||
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
|
||||
getActivity().startActivity(intent);
|
||||
eventBus.post(new BottomSheetLockEvent(true, 0, false, true));
|
||||
} else if (operationCode != 10) {
|
||||
if (!proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(true);
|
||||
proceedButton.setAlpha(1.0f);
|
||||
}
|
||||
} else if (operationCode != 11) {
|
||||
eventBus.post(new BottomSheetLockEvent(false, 0, false, false));
|
||||
bundle = new Bundle();
|
||||
bundle.putInt(BundleKeys.INSTANCE.getKEY_OPERATION_CODE(), operationCode);
|
||||
bundle.putString(BundleKeys.INSTANCE.getKEY_CALL_URL(), editText.getText().toString());
|
||||
getRouter().pushController(RouterTransaction.with(new OperationsMenuController(bundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
|
||||
} else if (operationCode == 11) {
|
||||
eventBus.post(new BottomSheetLockEvent(false, 0, false, false));
|
||||
originalBundle.putString(BundleKeys.INSTANCE.getKEY_CONVERSATION_NAME(), editText.getText().toString());
|
||||
getRouter().pushController(RouterTransaction.with(new OperationsMenuController(originalBundle))
|
||||
.pushChangeHandler(new HorizontalChangeHandler())
|
||||
.popChangeHandler(new HorizontalChangeHandler()));
|
||||
|
||||
textInputLayout.setErrorEnabled(false);
|
||||
} else if ((editText.getText().toString().startsWith("http://") ||
|
||||
editText.getText().toString().startsWith("https://")) &&
|
||||
editText.getText().toString().contains("/call/")) {
|
||||
// operation code 10
|
||||
if (!proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(true);
|
||||
proceedButton.setAlpha(1.0f);
|
||||
}
|
||||
textInputLayout.setErrorEnabled(false);
|
||||
} else {
|
||||
if (proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(false);
|
||||
proceedButton.setAlpha(0.38f);
|
||||
}
|
||||
textInputLayout.setError(getResources().getString(R.string.nc_wrong_link));
|
||||
}
|
||||
} else {
|
||||
if (proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(false);
|
||||
proceedButton.setAlpha(0.38f);
|
||||
}
|
||||
textInputLayout.setErrorEnabled(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
@Override
|
||||
protected void onViewBound(@NonNull View view) {
|
||||
super.onViewBound(view);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
|
||||
if (conversation != null && operationCode == 2) {
|
||||
editText.setText(conversation.getName());
|
||||
}
|
||||
|
||||
editText.setOnEditorActionListener((v, actionId, event) -> {
|
||||
if (actionId == EditorInfo.IME_ACTION_DONE && proceedButton != null && proceedButton.isEnabled()) {
|
||||
proceedButton.callOnClick();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
});
|
||||
|
||||
editText.addTextChangedListener(new TextWatcher() {
|
||||
@Override
|
||||
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onTextChanged(CharSequence s, int start, int before, int count) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterTextChanged(Editable s) {
|
||||
if (!TextUtils.isEmpty(s)) {
|
||||
if (operationCode == 2) {
|
||||
if (conversation.getName() == null || !conversation.getName().equals(s.toString())) {
|
||||
if (!proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(true);
|
||||
proceedButton.setAlpha(1.0f);
|
||||
}
|
||||
textInputLayout.setErrorEnabled(false);
|
||||
} else {
|
||||
if (proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(false);
|
||||
proceedButton.setAlpha(0.38f);
|
||||
}
|
||||
textInputLayout.setError(getResources().getString(R.string.nc_call_name_is_same));
|
||||
}
|
||||
} else if (operationCode != 10) {
|
||||
if (!proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(true);
|
||||
proceedButton.setAlpha(1.0f);
|
||||
}
|
||||
textInputLayout.setErrorEnabled(false);
|
||||
} else if ((editText.getText().toString().startsWith("http://") ||
|
||||
editText.getText().toString().startsWith("https://")) &&
|
||||
editText.getText().toString().contains("/call/")) {
|
||||
// operation code 10
|
||||
if (!proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(true);
|
||||
proceedButton.setAlpha(1.0f);
|
||||
}
|
||||
textInputLayout.setErrorEnabled(false);
|
||||
} else {
|
||||
if (proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(false);
|
||||
proceedButton.setAlpha(0.38f);
|
||||
}
|
||||
textInputLayout.setError(getResources().getString(R.string.nc_wrong_link));
|
||||
}
|
||||
} else {
|
||||
if (proceedButton.isEnabled()) {
|
||||
proceedButton.setEnabled(false);
|
||||
proceedButton.setAlpha(0.38f);
|
||||
}
|
||||
textInputLayout.setErrorEnabled(false);
|
||||
String labelText = "";
|
||||
switch (operationCode) {
|
||||
case 11:
|
||||
case 2:
|
||||
labelText = getResources().getString(R.string.nc_call_name);
|
||||
editText.setInputType(InputType.TYPE_CLASS_TEXT);
|
||||
smileyButton.setVisibility(View.VISIBLE);
|
||||
emojiPopup = EmojiPopup.Builder.fromRootView(view)
|
||||
.setOnEmojiPopupShownListener(new OnEmojiPopupShownListener() {
|
||||
@Override
|
||||
public void onEmojiPopupShown() {
|
||||
if (getResources() != null) {
|
||||
smileyButton.setColorFilter(getResources().getColor(R.color.colorPrimary),
|
||||
PorterDuff.Mode.SRC_IN);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
})
|
||||
.setOnEmojiPopupDismissListener(new OnEmojiPopupDismissListener() {
|
||||
@Override
|
||||
public void onEmojiPopupDismiss() {
|
||||
if (smileyButton != null) {
|
||||
smileyButton.setColorFilter(getResources().getColor(R.color.emoji_icons),
|
||||
PorterDuff.Mode.SRC_IN);
|
||||
}
|
||||
}
|
||||
})
|
||||
.setOnEmojiClickListener(new OnEmojiClickListener() {
|
||||
@Override
|
||||
public void onEmojiClick(@NonNull EmojiImageView emoji, @NonNull Emoji imageView) {
|
||||
editText.getEditableText().append(" ");
|
||||
}
|
||||
})
|
||||
.build(editText);
|
||||
|
||||
String labelText = "";
|
||||
switch (operationCode) {
|
||||
case 11:
|
||||
case 2:
|
||||
labelText = getResources().getString(R.string.nc_call_name);
|
||||
editText.setInputType(InputType.TYPE_CLASS_TEXT);
|
||||
smileyButton.setVisibility(View.VISIBLE);
|
||||
emojiPopup = EmojiPopup.Builder.fromRootView(view).setOnEmojiPopupShownListener(new OnEmojiPopupShownListener() {
|
||||
@Override
|
||||
public void onEmojiPopupShown() {
|
||||
if (getResources() != null) {
|
||||
smileyButton.setColorFilter(getResources().getColor(R.color.colorPrimary),
|
||||
PorterDuff.Mode.SRC_IN);
|
||||
}
|
||||
}
|
||||
}).setOnEmojiPopupDismissListener(new OnEmojiPopupDismissListener() {
|
||||
@Override
|
||||
public void onEmojiPopupDismiss() {
|
||||
if (smileyButton != null) {
|
||||
smileyButton.setColorFilter(getResources().getColor(R.color.emoji_icons),
|
||||
PorterDuff.Mode.SRC_IN);
|
||||
}
|
||||
}
|
||||
}).setOnEmojiClickListener(new OnEmojiClickListener() {
|
||||
@Override
|
||||
public void onEmojiClick(@NonNull EmojiImageView emoji, @NonNull Emoji imageView) {
|
||||
editText.getEditableText().append(" ");
|
||||
}
|
||||
}).build(editText);
|
||||
|
||||
break;
|
||||
case 4:
|
||||
labelText = getResources().getString(R.string.nc_new_password);
|
||||
editText.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_PASSWORD);
|
||||
break;
|
||||
case 6:
|
||||
case 7:
|
||||
case 99:
|
||||
// 99 is joining a conversation via password
|
||||
labelText = getResources().getString(R.string.nc_password);
|
||||
editText.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_PASSWORD);
|
||||
break;
|
||||
case 10:
|
||||
labelText = getResources().getString(R.string.nc_conversation_link);
|
||||
editText.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_URI);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
textInputLayout.setPasswordVisibilityToggleEnabled(operationCode == 99 || operationCode == 4 || operationCode == 6 || operationCode == 7);
|
||||
textInputLayout.setHint(labelText);
|
||||
textInputLayout.requestFocus();
|
||||
break;
|
||||
case 4:
|
||||
labelText = getResources().getString(R.string.nc_new_password);
|
||||
editText.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_PASSWORD);
|
||||
break;
|
||||
case 6:
|
||||
case 7:
|
||||
case 99:
|
||||
// 99 is joining a conversation via password
|
||||
labelText = getResources().getString(R.string.nc_password);
|
||||
editText.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_PASSWORD);
|
||||
break;
|
||||
case 10:
|
||||
labelText = getResources().getString(R.string.nc_conversation_link);
|
||||
editText.setInputType(InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_URI);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
textInputLayout.setPasswordVisibilityToggleEnabled(
|
||||
operationCode == 99 || operationCode == 4 || operationCode == 6 || operationCode == 7);
|
||||
textInputLayout.setHint(labelText);
|
||||
textInputLayout.requestFocus();
|
||||
}
|
||||
}
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -24,15 +24,16 @@ import android.widget.ImageView
|
||||
import androidx.annotation.DrawableRes
|
||||
|
||||
interface ListItemWithImage {
|
||||
val title: String
|
||||
fun populateIcon(imageView: ImageView)
|
||||
val title: String
|
||||
fun populateIcon(imageView: ImageView)
|
||||
}
|
||||
|
||||
data class BasicListItemWithImage(
|
||||
@DrawableRes val iconRes: Int,
|
||||
override val title: String) : ListItemWithImage {
|
||||
@DrawableRes val iconRes: Int,
|
||||
override val title: String
|
||||
) : ListItemWithImage {
|
||||
|
||||
override fun populateIcon(imageView: ImageView) {
|
||||
imageView.setImageResource(iconRes)
|
||||
}
|
||||
override fun populateIcon(imageView: ImageView) {
|
||||
imageView.setImageResource(iconRes)
|
||||
}
|
||||
}
|
@ -38,112 +38,117 @@ import com.nextcloud.talk.R
|
||||
private const val KEY_ACTIVATED_INDEX = "activated_index"
|
||||
|
||||
internal class ListItemViewHolder(
|
||||
itemView: View,
|
||||
private val adapter: ListIconDialogAdapter<*>) : RecyclerView.ViewHolder(itemView), View.OnClickListener {
|
||||
init {
|
||||
itemView.setOnClickListener(this)
|
||||
}
|
||||
itemView: View,
|
||||
private val adapter: ListIconDialogAdapter<*>
|
||||
) : RecyclerView.ViewHolder(itemView), View.OnClickListener {
|
||||
init {
|
||||
itemView.setOnClickListener(this)
|
||||
}
|
||||
|
||||
val iconView: ImageView = itemView.findViewById(R.id.icon)
|
||||
val titleView: RtlTextView = itemView.findViewById(R.id.title)
|
||||
val iconView: ImageView = itemView.findViewById(R.id.icon)
|
||||
val titleView: RtlTextView = itemView.findViewById(R.id.title)
|
||||
|
||||
override fun onClick(view: View) = adapter.itemClicked(adapterPosition)
|
||||
override fun onClick(view: View) = adapter.itemClicked(adapterPosition)
|
||||
}
|
||||
|
||||
internal class ListIconDialogAdapter<IT : ListItemWithImage>(
|
||||
private var dialog: MaterialDialog,
|
||||
private var items: List<IT>,
|
||||
disabledItems: IntArray?,
|
||||
private var waitForPositiveButton: Boolean,
|
||||
private var selection: ListItemListener<IT>) : RecyclerView.Adapter<ListItemViewHolder>(), DialogAdapter<IT, ListItemListener<IT>> {
|
||||
private var dialog: MaterialDialog,
|
||||
private var items: List<IT>,
|
||||
disabledItems: IntArray?,
|
||||
private var waitForPositiveButton: Boolean,
|
||||
private var selection: ListItemListener<IT>
|
||||
) : RecyclerView.Adapter<ListItemViewHolder>(), DialogAdapter<IT, ListItemListener<IT>> {
|
||||
|
||||
private var disabledIndices: IntArray = disabledItems ?: IntArray(0)
|
||||
private var disabledIndices: IntArray = disabledItems ?: IntArray(0)
|
||||
|
||||
fun itemClicked(index: Int) {
|
||||
if (waitForPositiveButton && dialog.hasActionButton(WhichButton.POSITIVE)) {
|
||||
// Wait for positive action button, mark clicked item as activated so that we can call the
|
||||
// selection listener when the button is pressed.
|
||||
val lastActivated = dialog.config[KEY_ACTIVATED_INDEX] as? Int
|
||||
dialog.config[KEY_ACTIVATED_INDEX] = index
|
||||
if (lastActivated != null) {
|
||||
notifyItemChanged(lastActivated)
|
||||
}
|
||||
notifyItemChanged(index)
|
||||
} else {
|
||||
// Don't wait for action buttons, call listener and dismiss if auto dismiss is applicable
|
||||
this.selection?.invoke(dialog, index, this.items[index])
|
||||
if (dialog.autoDismissEnabled && !dialog.hasActionButtons()) {
|
||||
dialog.dismiss()
|
||||
}
|
||||
}
|
||||
fun itemClicked(index: Int) {
|
||||
if (waitForPositiveButton && dialog.hasActionButton(WhichButton.POSITIVE)) {
|
||||
// Wait for positive action button, mark clicked item as activated so that we can call the
|
||||
// selection listener when the button is pressed.
|
||||
val lastActivated = dialog.config[KEY_ACTIVATED_INDEX] as? Int
|
||||
dialog.config[KEY_ACTIVATED_INDEX] = index
|
||||
if (lastActivated != null) {
|
||||
notifyItemChanged(lastActivated)
|
||||
}
|
||||
notifyItemChanged(index)
|
||||
} else {
|
||||
// Don't wait for action buttons, call listener and dismiss if auto dismiss is applicable
|
||||
this.selection?.invoke(dialog, index, this.items[index])
|
||||
if (dialog.autoDismissEnabled && !dialog.hasActionButtons()) {
|
||||
dialog.dismiss()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun onCreateViewHolder(
|
||||
parent: ViewGroup,
|
||||
viewType: Int): ListItemViewHolder {
|
||||
val listItemView: View = parent.inflate(dialog.windowContext, R.layout.menu_item_sheet)
|
||||
val viewHolder = ListItemViewHolder(
|
||||
itemView = listItemView,
|
||||
adapter = this
|
||||
)
|
||||
viewHolder.titleView.maybeSetTextColor(dialog.windowContext, R.attr.md_color_content)
|
||||
return viewHolder
|
||||
override fun onCreateViewHolder(
|
||||
parent: ViewGroup,
|
||||
viewType: Int
|
||||
): ListItemViewHolder {
|
||||
val listItemView: View = parent.inflate(dialog.windowContext, R.layout.menu_item_sheet)
|
||||
val viewHolder = ListItemViewHolder(
|
||||
itemView = listItemView,
|
||||
adapter = this
|
||||
)
|
||||
viewHolder.titleView.maybeSetTextColor(dialog.windowContext, R.attr.md_color_content)
|
||||
return viewHolder
|
||||
}
|
||||
|
||||
override fun getItemCount() = items.size
|
||||
|
||||
override fun onBindViewHolder(
|
||||
holder: ListItemViewHolder,
|
||||
position: Int
|
||||
) {
|
||||
holder.itemView.isEnabled = !disabledIndices.contains(position)
|
||||
val currentItem = items[position]
|
||||
|
||||
holder.titleView.text = currentItem.title
|
||||
holder.itemView.background = dialog.getItemSelector()
|
||||
currentItem.populateIcon(holder.iconView)
|
||||
|
||||
val activatedIndex = dialog.config[KEY_ACTIVATED_INDEX] as? Int
|
||||
holder.itemView.isActivated = activatedIndex != null && activatedIndex == position
|
||||
|
||||
if (dialog.bodyFont != null) {
|
||||
holder.titleView.typeface = dialog.bodyFont
|
||||
}
|
||||
}
|
||||
|
||||
override fun getItemCount() = items.size
|
||||
|
||||
override fun onBindViewHolder(
|
||||
holder: ListItemViewHolder,
|
||||
position: Int) {
|
||||
holder.itemView.isEnabled = !disabledIndices.contains(position)
|
||||
val currentItem = items[position]
|
||||
|
||||
holder.titleView.text = currentItem.title
|
||||
holder.itemView.background = dialog.getItemSelector()
|
||||
currentItem.populateIcon(holder.iconView)
|
||||
|
||||
val activatedIndex = dialog.config[KEY_ACTIVATED_INDEX] as? Int
|
||||
holder.itemView.isActivated = activatedIndex != null && activatedIndex == position
|
||||
|
||||
if (dialog.bodyFont != null) {
|
||||
holder.titleView.typeface = dialog.bodyFont
|
||||
}
|
||||
override fun positiveButtonClicked() {
|
||||
val activatedIndex = dialog.config[KEY_ACTIVATED_INDEX] as? Int
|
||||
if (activatedIndex != null) {
|
||||
selection?.invoke(dialog, activatedIndex, items[activatedIndex])
|
||||
dialog.config.remove(KEY_ACTIVATED_INDEX)
|
||||
}
|
||||
}
|
||||
|
||||
override fun positiveButtonClicked() {
|
||||
val activatedIndex = dialog.config[KEY_ACTIVATED_INDEX] as? Int
|
||||
if (activatedIndex != null) {
|
||||
selection?.invoke(dialog, activatedIndex, items[activatedIndex])
|
||||
dialog.config.remove(KEY_ACTIVATED_INDEX)
|
||||
}
|
||||
override fun replaceItems(
|
||||
items: List<IT>,
|
||||
listener: ListItemListener<IT>
|
||||
) {
|
||||
this.items = items
|
||||
if (listener != null) {
|
||||
this.selection = listener
|
||||
}
|
||||
this.notifyDataSetChanged()
|
||||
}
|
||||
|
||||
override fun replaceItems(
|
||||
items: List<IT>,
|
||||
listener: ListItemListener<IT>) {
|
||||
this.items = items
|
||||
if (listener != null) {
|
||||
this.selection = listener
|
||||
}
|
||||
this.notifyDataSetChanged()
|
||||
}
|
||||
override fun disableItems(indices: IntArray) {
|
||||
this.disabledIndices = indices
|
||||
notifyDataSetChanged()
|
||||
}
|
||||
|
||||
override fun disableItems(indices: IntArray) {
|
||||
this.disabledIndices = indices
|
||||
notifyDataSetChanged()
|
||||
}
|
||||
override fun checkItems(indices: IntArray) = Unit
|
||||
|
||||
override fun checkItems(indices: IntArray) = Unit
|
||||
override fun uncheckItems(indices: IntArray) = Unit
|
||||
|
||||
override fun uncheckItems(indices: IntArray) = Unit
|
||||
override fun toggleItems(indices: IntArray) = Unit
|
||||
|
||||
override fun toggleItems(indices: IntArray) = Unit
|
||||
override fun checkAllItems() = Unit
|
||||
|
||||
override fun checkAllItems() = Unit
|
||||
override fun uncheckAllItems() = Unit
|
||||
|
||||
override fun uncheckAllItems() = Unit
|
||||
override fun toggleAllChecked() = Unit
|
||||
|
||||
override fun toggleAllChecked() = Unit
|
||||
|
||||
override fun isItemChecked(index: Int) = false
|
||||
override fun isItemChecked(index: Int) = false
|
||||
}
|
||||
|
@ -28,48 +28,50 @@ import com.afollestad.materialdialogs.list.customListAdapter
|
||||
import com.afollestad.materialdialogs.list.getListAdapter
|
||||
|
||||
typealias ListItemListener<IT> =
|
||||
((dialog: MaterialDialog, index: Int, item: IT) -> Unit)?
|
||||
((dialog: MaterialDialog, index: Int, item: IT) -> Unit)?
|
||||
|
||||
@CheckResult fun <IT : ListItemWithImage> MaterialDialog.listItemsWithImage(
|
||||
items: List<IT>,
|
||||
disabledIndices: IntArray? = null,
|
||||
waitForPositiveButton: Boolean = true,
|
||||
selection: ListItemListener<IT> = null): MaterialDialog {
|
||||
items: List<IT>,
|
||||
disabledIndices: IntArray? = null,
|
||||
waitForPositiveButton: Boolean = true,
|
||||
selection: ListItemListener<IT> = null
|
||||
): MaterialDialog {
|
||||
|
||||
if (getListAdapter() != null) {
|
||||
return updateListItemsWithImage(
|
||||
items = items,
|
||||
disabledIndices = disabledIndices
|
||||
)
|
||||
}
|
||||
|
||||
val layoutManager = LinearLayoutManager(windowContext)
|
||||
return customListAdapter(
|
||||
adapter = ListIconDialogAdapter(
|
||||
dialog = this,
|
||||
items = items,
|
||||
disabledItems = disabledIndices,
|
||||
waitForPositiveButton = waitForPositiveButton,
|
||||
selection = selection
|
||||
),
|
||||
layoutManager = layoutManager
|
||||
if (getListAdapter() != null) {
|
||||
return updateListItemsWithImage(
|
||||
items = items,
|
||||
disabledIndices = disabledIndices
|
||||
)
|
||||
}
|
||||
|
||||
val layoutManager = LinearLayoutManager(windowContext)
|
||||
return customListAdapter(
|
||||
adapter = ListIconDialogAdapter(
|
||||
dialog = this,
|
||||
items = items,
|
||||
disabledItems = disabledIndices,
|
||||
waitForPositiveButton = waitForPositiveButton,
|
||||
selection = selection
|
||||
),
|
||||
layoutManager = layoutManager
|
||||
)
|
||||
}
|
||||
|
||||
fun MaterialDialog.updateListItemsWithImage(
|
||||
items: List<ListItemWithImage>,
|
||||
disabledIndices: IntArray? = null): MaterialDialog {
|
||||
val adapter = getListAdapter()
|
||||
check(adapter != null) {
|
||||
"updateGridItems(...) can't be used before you've created a bottom sheet grid dialog."
|
||||
}
|
||||
if (adapter is DialogAdapter<*, *>) {
|
||||
@Suppress("UNCHECKED_CAST")
|
||||
(adapter as DialogAdapter<ListItemWithImage, *>).replaceItems(items)
|
||||
items: List<ListItemWithImage>,
|
||||
disabledIndices: IntArray? = null
|
||||
): MaterialDialog {
|
||||
val adapter = getListAdapter()
|
||||
check(adapter != null) {
|
||||
"updateGridItems(...) can't be used before you've created a bottom sheet grid dialog."
|
||||
}
|
||||
if (adapter is DialogAdapter<*, *>) {
|
||||
@Suppress("UNCHECKED_CAST")
|
||||
(adapter as DialogAdapter<ListItemWithImage, *>).replaceItems(items)
|
||||
|
||||
if (disabledIndices != null) {
|
||||
adapter.disableItems(disabledIndices)
|
||||
}
|
||||
if (disabledIndices != null) {
|
||||
adapter.disableItems(disabledIndices)
|
||||
}
|
||||
return this
|
||||
}
|
||||
return this
|
||||
}
|
||||
|
@ -28,9 +28,9 @@ import org.greenrobot.eventbus.EventBus;
|
||||
@Module
|
||||
public class BusModule {
|
||||
|
||||
@Provides
|
||||
@Singleton
|
||||
public EventBus provideEventBus() {
|
||||
return EventBus.getDefault();
|
||||
}
|
||||
@Provides
|
||||
@Singleton
|
||||
public EventBus provideEventBus() {
|
||||
return EventBus.getDefault();
|
||||
}
|
||||
}
|
@ -27,14 +27,14 @@ import dagger.Provides;
|
||||
|
||||
@Module
|
||||
public class ContextModule {
|
||||
private final Context context;
|
||||
private final Context context;
|
||||
|
||||
public ContextModule(@NonNull final Context context) {
|
||||
this.context = context;
|
||||
}
|
||||
public ContextModule(@NonNull final Context context) {
|
||||
this.context = context;
|
||||
}
|
||||
|
||||
@Provides
|
||||
public Context provideContext() {
|
||||
return context;
|
||||
}
|
||||
@Provides
|
||||
public Context provideContext() {
|
||||
return context;
|
||||
}
|
||||
}
|
||||
|
@ -39,25 +39,26 @@ import net.orange_box.storebox.StoreBox;
|
||||
@Module
|
||||
public class DatabaseModule {
|
||||
|
||||
@Provides
|
||||
@Singleton
|
||||
public SqlCipherDatabaseSource provideSqlCipherDatabaseSource(@NonNull final Context context) {
|
||||
return new SqlCipherDatabaseSource(context, Models.DEFAULT,
|
||||
context.getResources().getString(R.string.nc_app_name).toLowerCase()
|
||||
.replace(" ", "_").trim() + ".sqlite",
|
||||
context.getString(R.string.nc_talk_database_encryption_key), 6);
|
||||
}
|
||||
@Provides
|
||||
@Singleton
|
||||
public SqlCipherDatabaseSource provideSqlCipherDatabaseSource(@NonNull final Context context) {
|
||||
return new SqlCipherDatabaseSource(context, Models.DEFAULT,
|
||||
context.getResources().getString(R.string.nc_app_name).toLowerCase()
|
||||
.replace(" ", "_").trim() + ".sqlite",
|
||||
context.getString(R.string.nc_talk_database_encryption_key), 6);
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Singleton
|
||||
public ReactiveEntityStore<Persistable> provideDataStore(@NonNull final SqlCipherDatabaseSource sqlCipherDatabaseSource) {
|
||||
final Configuration configuration = sqlCipherDatabaseSource.getConfiguration();
|
||||
return ReactiveSupport.toReactiveStore(new EntityDataStore<Persistable>(configuration));
|
||||
}
|
||||
@Provides
|
||||
@Singleton
|
||||
public ReactiveEntityStore<Persistable> provideDataStore(
|
||||
@NonNull final SqlCipherDatabaseSource sqlCipherDatabaseSource) {
|
||||
final Configuration configuration = sqlCipherDatabaseSource.getConfiguration();
|
||||
return ReactiveSupport.toReactiveStore(new EntityDataStore<Persistable>(configuration));
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Singleton
|
||||
public AppPreferences providePreferences(@NonNull final Context poContext) {
|
||||
return StoreBox.create(poContext, AppPreferences.class);
|
||||
}
|
||||
@Provides
|
||||
@Singleton
|
||||
public AppPreferences providePreferences(@NonNull final Context poContext) {
|
||||
return StoreBox.create(poContext, AppPreferences.class);
|
||||
}
|
||||
}
|
||||
|
@ -73,250 +73,253 @@ import retrofit2.adapter.rxjava2.RxJava2CallAdapterFactory;
|
||||
@Module(includes = DatabaseModule.class)
|
||||
public class RestModule {
|
||||
|
||||
private static final String TAG = "RestModule";
|
||||
private final Context context;
|
||||
private static final String TAG = "RestModule";
|
||||
private final Context context;
|
||||
|
||||
public RestModule(Context context) {
|
||||
this.context = context;
|
||||
public RestModule(Context context) {
|
||||
this.context = context;
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
NcApi provideNcApi(Retrofit retrofit) {
|
||||
return retrofit.create(NcApi.class);
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
Proxy provideProxy(AppPreferences appPreferences) {
|
||||
if (!TextUtils.isEmpty(appPreferences.getProxyType()) && !"No proxy".equals(
|
||||
appPreferences.getProxyType())
|
||||
&& !TextUtils.isEmpty(appPreferences.getProxyHost())) {
|
||||
GetProxyRunnable getProxyRunnable = new GetProxyRunnable(appPreferences);
|
||||
Thread getProxyThread = new Thread(getProxyRunnable);
|
||||
getProxyThread.start();
|
||||
try {
|
||||
getProxyThread.join();
|
||||
return getProxyRunnable.getProxyValue();
|
||||
} catch (InterruptedException e) {
|
||||
Log.e(TAG, "Failed to join the thread while getting proxy: " + e.getLocalizedMessage());
|
||||
return Proxy.NO_PROXY;
|
||||
}
|
||||
} else {
|
||||
return Proxy.NO_PROXY;
|
||||
}
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
Retrofit provideRetrofit(OkHttpClient httpClient) {
|
||||
Retrofit.Builder retrofitBuilder = new Retrofit.Builder()
|
||||
.client(httpClient)
|
||||
.baseUrl("https://nextcloud.com")
|
||||
.addCallAdapterFactory(RxJava2CallAdapterFactory.createWithScheduler(Schedulers.io()))
|
||||
.addConverterFactory(LoganSquareConverterFactory.create());
|
||||
|
||||
return retrofitBuilder.build();
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
MagicTrustManager provideMagicTrustManager() {
|
||||
return new MagicTrustManager();
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
MagicKeyManager provideKeyManager(AppPreferences appPreferences, UserUtils userUtils) {
|
||||
KeyStore keyStore = null;
|
||||
try {
|
||||
keyStore = KeyStore.getInstance("AndroidKeyStore");
|
||||
keyStore.load(null);
|
||||
KeyManagerFactory kmf =
|
||||
KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
|
||||
kmf.init(keyStore, null);
|
||||
X509KeyManager origKm = (X509KeyManager) kmf.getKeyManagers()[0];
|
||||
return new MagicKeyManager(origKm, userUtils, appPreferences);
|
||||
} catch (KeyStoreException e) {
|
||||
Log.e(TAG, "KeyStoreException " + e.getLocalizedMessage());
|
||||
} catch (CertificateException e) {
|
||||
Log.e(TAG, "CertificateException " + e.getLocalizedMessage());
|
||||
} catch (NoSuchAlgorithmException e) {
|
||||
Log.e(TAG, "NoSuchAlgorithmException " + e.getLocalizedMessage());
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "IOException " + e.getLocalizedMessage());
|
||||
} catch (UnrecoverableKeyException e) {
|
||||
Log.e(TAG, "UnrecoverableKeyException " + e.getLocalizedMessage());
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
NcApi provideNcApi(Retrofit retrofit) {
|
||||
return retrofit.create(NcApi.class);
|
||||
return null;
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
SSLSocketFactoryCompat provideSslSocketFactoryCompat(MagicKeyManager keyManager, MagicTrustManager
|
||||
magicTrustManager) {
|
||||
return new SSLSocketFactoryCompat(keyManager, magicTrustManager);
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
CookieManager provideCookieManager() {
|
||||
CookieManager cookieManager = new CookieManager();
|
||||
cookieManager.setCookiePolicy(CookiePolicy.ACCEPT_NONE);
|
||||
return cookieManager;
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
Cache provideCache() {
|
||||
int cacheSize = 128 * 1024 * 1024; // 128 MB
|
||||
return new Cache(NextcloudTalkApplication.Companion.getSharedApplication().getCacheDir(),
|
||||
cacheSize);
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
Dispatcher provideDispatcher() {
|
||||
Dispatcher dispatcher = new Dispatcher();
|
||||
dispatcher.setMaxRequestsPerHost(100);
|
||||
dispatcher.setMaxRequests(100);
|
||||
return dispatcher;
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
OkHttpClient provideHttpClient(Proxy proxy, AppPreferences appPreferences,
|
||||
MagicTrustManager magicTrustManager,
|
||||
SSLSocketFactoryCompat sslSocketFactoryCompat, Cache cache,
|
||||
CookieManager cookieManager, Dispatcher dispatcher) {
|
||||
OkHttpClient.Builder httpClient = new OkHttpClient.Builder();
|
||||
|
||||
httpClient.retryOnConnectionFailure(true);
|
||||
httpClient.connectTimeout(45, TimeUnit.SECONDS);
|
||||
httpClient.readTimeout(45, TimeUnit.SECONDS);
|
||||
httpClient.writeTimeout(45, TimeUnit.SECONDS);
|
||||
|
||||
httpClient.cookieJar(new JavaNetCookieJar(cookieManager));
|
||||
httpClient.cache(cache);
|
||||
|
||||
// Trust own CA and all self-signed certs
|
||||
httpClient.sslSocketFactory(sslSocketFactoryCompat, magicTrustManager);
|
||||
httpClient.retryOnConnectionFailure(true);
|
||||
httpClient.hostnameVerifier(magicTrustManager.getHostnameVerifier(OkHostnameVerifier.INSTANCE));
|
||||
|
||||
httpClient.dispatcher(dispatcher);
|
||||
if (!Proxy.NO_PROXY.equals(proxy)) {
|
||||
httpClient.proxy(proxy);
|
||||
|
||||
if (appPreferences.getProxyCredentials() &&
|
||||
!TextUtils.isEmpty(appPreferences.getProxyUsername()) &&
|
||||
!TextUtils.isEmpty(appPreferences.getProxyPassword())) {
|
||||
httpClient.proxyAuthenticator(new MagicAuthenticator(Credentials.basic(
|
||||
appPreferences.getProxyUsername(),
|
||||
appPreferences.getProxyPassword()), "Proxy-Authorization"));
|
||||
}
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
Proxy provideProxy(AppPreferences appPreferences) {
|
||||
if (!TextUtils.isEmpty(appPreferences.getProxyType()) && !"No proxy".equals(appPreferences.getProxyType())
|
||||
&& !TextUtils.isEmpty(appPreferences.getProxyHost())) {
|
||||
GetProxyRunnable getProxyRunnable = new GetProxyRunnable(appPreferences);
|
||||
Thread getProxyThread = new Thread(getProxyRunnable);
|
||||
getProxyThread.start();
|
||||
try {
|
||||
getProxyThread.join();
|
||||
return getProxyRunnable.getProxyValue();
|
||||
} catch (InterruptedException e) {
|
||||
Log.e(TAG, "Failed to join the thread while getting proxy: " + e.getLocalizedMessage());
|
||||
return Proxy.NO_PROXY;
|
||||
}
|
||||
} else {
|
||||
return Proxy.NO_PROXY;
|
||||
}
|
||||
httpClient.addInterceptor(new HeadersInterceptor());
|
||||
|
||||
if (BuildConfig.DEBUG && !context.getResources().getBoolean(R.bool.nc_is_debug)) {
|
||||
HttpLoggingInterceptor loggingInterceptor = new HttpLoggingInterceptor();
|
||||
loggingInterceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
|
||||
loggingInterceptor.redactHeader("Authorization");
|
||||
loggingInterceptor.redactHeader("Proxy-Authorization");
|
||||
httpClient.addInterceptor(loggingInterceptor);
|
||||
} else if (context.getResources().getBoolean(R.bool.nc_is_debug)) {
|
||||
|
||||
HttpLoggingInterceptor.Logger fileLogger =
|
||||
s -> LoggingUtils.INSTANCE.writeLogEntryToFile(context, s);
|
||||
HttpLoggingInterceptor loggingInterceptor = new HttpLoggingInterceptor(fileLogger);
|
||||
loggingInterceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
|
||||
loggingInterceptor.redactHeader("Authorization");
|
||||
loggingInterceptor.redactHeader("Proxy-Authorization");
|
||||
httpClient.addInterceptor(loggingInterceptor);
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
Retrofit provideRetrofit(OkHttpClient httpClient) {
|
||||
Retrofit.Builder retrofitBuilder = new Retrofit.Builder()
|
||||
.client(httpClient)
|
||||
.baseUrl("https://nextcloud.com")
|
||||
.addCallAdapterFactory(RxJava2CallAdapterFactory.createWithScheduler(Schedulers.io()))
|
||||
.addConverterFactory(LoganSquareConverterFactory.create());
|
||||
return httpClient.build();
|
||||
}
|
||||
|
||||
return retrofitBuilder.build();
|
||||
public static class HeadersInterceptor implements Interceptor {
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Response intercept(@NonNull Chain chain) throws IOException {
|
||||
Request original = chain.request();
|
||||
Request request = original.newBuilder()
|
||||
.header("User-Agent", ApiUtils.getUserAgent())
|
||||
.header("Accept", "application/json")
|
||||
.header("OCS-APIRequest", "true")
|
||||
.method(original.method(), original.body())
|
||||
.build();
|
||||
|
||||
Response response = chain.proceed(request);
|
||||
|
||||
if (request.url().encodedPath().contains("/avatar/")) {
|
||||
AvatarStatusCodeHolder.getInstance().setStatusCode(response.code());
|
||||
}
|
||||
|
||||
return response;
|
||||
}
|
||||
}
|
||||
|
||||
public static class MagicAuthenticator implements Authenticator {
|
||||
|
||||
private String credentials;
|
||||
private String authenticatorType;
|
||||
|
||||
public MagicAuthenticator(@NonNull String credentials, @NonNull String authenticatorType) {
|
||||
this.credentials = credentials;
|
||||
this.authenticatorType = authenticatorType;
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
MagicTrustManager provideMagicTrustManager() {
|
||||
return new MagicTrustManager();
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
MagicKeyManager provideKeyManager(AppPreferences appPreferences, UserUtils userUtils) {
|
||||
KeyStore keyStore = null;
|
||||
try {
|
||||
keyStore = KeyStore.getInstance("AndroidKeyStore");
|
||||
keyStore.load(null);
|
||||
KeyManagerFactory kmf = KeyManagerFactory.getInstance(KeyManagerFactory.getDefaultAlgorithm());
|
||||
kmf.init(keyStore, null);
|
||||
X509KeyManager origKm = (X509KeyManager) kmf.getKeyManagers()[0];
|
||||
return new MagicKeyManager(origKm, userUtils, appPreferences);
|
||||
} catch (KeyStoreException e) {
|
||||
Log.e(TAG, "KeyStoreException " + e.getLocalizedMessage());
|
||||
} catch (CertificateException e) {
|
||||
Log.e(TAG, "CertificateException " + e.getLocalizedMessage());
|
||||
} catch (NoSuchAlgorithmException e) {
|
||||
Log.e(TAG, "NoSuchAlgorithmException " + e.getLocalizedMessage());
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "IOException " + e.getLocalizedMessage());
|
||||
} catch (UnrecoverableKeyException e) {
|
||||
Log.e(TAG, "UnrecoverableKeyException " + e.getLocalizedMessage());
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Request authenticate(@Nullable Route route, @NonNull Response response) {
|
||||
if (response.request().header(authenticatorType) != null) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
SSLSocketFactoryCompat provideSslSocketFactoryCompat(MagicKeyManager keyManager, MagicTrustManager
|
||||
magicTrustManager) {
|
||||
return new SSLSocketFactoryCompat(keyManager, magicTrustManager);
|
||||
}
|
||||
Response countedResponse = response;
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
CookieManager provideCookieManager() {
|
||||
CookieManager cookieManager = new CookieManager();
|
||||
cookieManager.setCookiePolicy(CookiePolicy.ACCEPT_NONE);
|
||||
return cookieManager;
|
||||
}
|
||||
int attemptsCount = 0;
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
Cache provideCache() {
|
||||
int cacheSize = 128 * 1024 * 1024; // 128 MB
|
||||
return new Cache(NextcloudTalkApplication.Companion.getSharedApplication().getCacheDir(), cacheSize);
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
Dispatcher provideDispatcher() {
|
||||
Dispatcher dispatcher = new Dispatcher();
|
||||
dispatcher.setMaxRequestsPerHost(100);
|
||||
dispatcher.setMaxRequests(100);
|
||||
return dispatcher;
|
||||
}
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
OkHttpClient provideHttpClient(Proxy proxy, AppPreferences appPreferences,
|
||||
MagicTrustManager magicTrustManager,
|
||||
SSLSocketFactoryCompat sslSocketFactoryCompat, Cache cache,
|
||||
CookieManager cookieManager, Dispatcher dispatcher) {
|
||||
OkHttpClient.Builder httpClient = new OkHttpClient.Builder();
|
||||
|
||||
httpClient.retryOnConnectionFailure(true);
|
||||
httpClient.connectTimeout(45, TimeUnit.SECONDS);
|
||||
httpClient.readTimeout(45, TimeUnit.SECONDS);
|
||||
httpClient.writeTimeout(45, TimeUnit.SECONDS);
|
||||
|
||||
httpClient.cookieJar(new JavaNetCookieJar(cookieManager));
|
||||
httpClient.cache(cache);
|
||||
|
||||
// Trust own CA and all self-signed certs
|
||||
httpClient.sslSocketFactory(sslSocketFactoryCompat, magicTrustManager);
|
||||
httpClient.retryOnConnectionFailure(true);
|
||||
httpClient.hostnameVerifier(magicTrustManager.getHostnameVerifier(OkHostnameVerifier.INSTANCE));
|
||||
|
||||
httpClient.dispatcher(dispatcher);
|
||||
if (!Proxy.NO_PROXY.equals(proxy)) {
|
||||
httpClient.proxy(proxy);
|
||||
|
||||
if (appPreferences.getProxyCredentials() &&
|
||||
!TextUtils.isEmpty(appPreferences.getProxyUsername()) &&
|
||||
!TextUtils.isEmpty(appPreferences.getProxyPassword())) {
|
||||
httpClient.proxyAuthenticator(new MagicAuthenticator(Credentials.basic(
|
||||
appPreferences.getProxyUsername(),
|
||||
appPreferences.getProxyPassword()), "Proxy-Authorization"));
|
||||
}
|
||||
while ((countedResponse = countedResponse.priorResponse()) != null) {
|
||||
attemptsCount++;
|
||||
if (attemptsCount == 3) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
httpClient.addInterceptor(new HeadersInterceptor());
|
||||
return response.request().newBuilder()
|
||||
.header(authenticatorType, credentials)
|
||||
.build();
|
||||
}
|
||||
}
|
||||
|
||||
if (BuildConfig.DEBUG && !context.getResources().getBoolean(R.bool.nc_is_debug)) {
|
||||
HttpLoggingInterceptor loggingInterceptor = new HttpLoggingInterceptor();
|
||||
loggingInterceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
|
||||
loggingInterceptor.redactHeader("Authorization");
|
||||
loggingInterceptor.redactHeader("Proxy-Authorization");
|
||||
httpClient.addInterceptor(loggingInterceptor);
|
||||
} else if (context.getResources().getBoolean(R.bool.nc_is_debug)) {
|
||||
private class GetProxyRunnable implements Runnable {
|
||||
private volatile Proxy proxy;
|
||||
private AppPreferences appPreferences;
|
||||
|
||||
HttpLoggingInterceptor.Logger fileLogger =
|
||||
s -> LoggingUtils.INSTANCE.writeLogEntryToFile(context, s);
|
||||
HttpLoggingInterceptor loggingInterceptor = new HttpLoggingInterceptor(fileLogger);
|
||||
loggingInterceptor.setLevel(HttpLoggingInterceptor.Level.BODY);
|
||||
loggingInterceptor.redactHeader("Authorization");
|
||||
loggingInterceptor.redactHeader("Proxy-Authorization");
|
||||
httpClient.addInterceptor(loggingInterceptor);
|
||||
}
|
||||
|
||||
return httpClient.build();
|
||||
GetProxyRunnable(AppPreferences appPreferences) {
|
||||
this.appPreferences = appPreferences;
|
||||
}
|
||||
|
||||
public static class HeadersInterceptor implements Interceptor {
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Response intercept(@NonNull Chain chain) throws IOException {
|
||||
Request original = chain.request();
|
||||
Request request = original.newBuilder()
|
||||
.header("User-Agent", ApiUtils.getUserAgent())
|
||||
.header("Accept", "application/json")
|
||||
.header("OCS-APIRequest", "true")
|
||||
.method(original.method(), original.body())
|
||||
.build();
|
||||
|
||||
Response response = chain.proceed(request);
|
||||
|
||||
if (request.url().encodedPath().contains("/avatar/")) {
|
||||
AvatarStatusCodeHolder.getInstance().setStatusCode(response.code());
|
||||
}
|
||||
|
||||
return response;
|
||||
}
|
||||
@Override
|
||||
public void run() {
|
||||
if (Proxy.Type.SOCKS.equals(Proxy.Type.valueOf(appPreferences.getProxyType()))) {
|
||||
proxy = new Proxy(Proxy.Type.valueOf(appPreferences.getProxyType()),
|
||||
InetSocketAddress.createUnresolved(appPreferences.getProxyHost(), Integer.parseInt(
|
||||
appPreferences.getProxyPort())));
|
||||
} else {
|
||||
proxy = new Proxy(Proxy.Type.valueOf(appPreferences.getProxyType()),
|
||||
new InetSocketAddress(appPreferences.getProxyHost(),
|
||||
Integer.parseInt(appPreferences.getProxyPort())));
|
||||
}
|
||||
}
|
||||
|
||||
public static class MagicAuthenticator implements Authenticator {
|
||||
|
||||
private String credentials;
|
||||
private String authenticatorType;
|
||||
|
||||
public MagicAuthenticator(@NonNull String credentials, @NonNull String authenticatorType) {
|
||||
this.credentials = credentials;
|
||||
this.authenticatorType = authenticatorType;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Request authenticate(@Nullable Route route, @NonNull Response response) {
|
||||
if (response.request().header(authenticatorType) != null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
Response countedResponse = response;
|
||||
|
||||
int attemptsCount = 0;
|
||||
|
||||
while ((countedResponse = countedResponse.priorResponse()) != null) {
|
||||
attemptsCount++;
|
||||
if (attemptsCount == 3) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
return response.request().newBuilder()
|
||||
.header(authenticatorType, credentials)
|
||||
.build();
|
||||
}
|
||||
}
|
||||
|
||||
private class GetProxyRunnable implements Runnable {
|
||||
private volatile Proxy proxy;
|
||||
private AppPreferences appPreferences;
|
||||
|
||||
GetProxyRunnable(AppPreferences appPreferences) {
|
||||
this.appPreferences = appPreferences;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
if (Proxy.Type.SOCKS.equals(Proxy.Type.valueOf(appPreferences.getProxyType()))) {
|
||||
proxy = new Proxy(Proxy.Type.valueOf(appPreferences.getProxyType()),
|
||||
InetSocketAddress.createUnresolved(appPreferences.getProxyHost(), Integer.parseInt(
|
||||
appPreferences.getProxyPort())));
|
||||
} else {
|
||||
proxy = new Proxy(Proxy.Type.valueOf(appPreferences.getProxyType()),
|
||||
new InetSocketAddress(appPreferences.getProxyHost(),
|
||||
Integer.parseInt(appPreferences.getProxyPort())));
|
||||
}
|
||||
}
|
||||
|
||||
Proxy getProxyValue() {
|
||||
return proxy;
|
||||
}
|
||||
Proxy getProxyValue() {
|
||||
return proxy;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -24,27 +24,28 @@ import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class BottomSheetLockEvent {
|
||||
private final boolean cancelable;
|
||||
private final int delay;
|
||||
private final boolean shouldRefreshData;
|
||||
private final boolean cancel;
|
||||
private boolean dismissView;
|
||||
private final boolean cancelable;
|
||||
private final int delay;
|
||||
private final boolean shouldRefreshData;
|
||||
private final boolean cancel;
|
||||
private boolean dismissView;
|
||||
|
||||
public BottomSheetLockEvent(boolean cancelable, int delay, boolean shouldRefreshData, boolean cancel) {
|
||||
this.cancelable = cancelable;
|
||||
this.delay = delay;
|
||||
this.shouldRefreshData = shouldRefreshData;
|
||||
this.cancel = cancel;
|
||||
this.dismissView = true;
|
||||
}
|
||||
|
||||
public BottomSheetLockEvent(boolean cancelable, int delay, boolean shouldRefreshData, boolean cancel, boolean
|
||||
dismissView) {
|
||||
this.cancelable = cancelable;
|
||||
this.delay = delay;
|
||||
this.shouldRefreshData = shouldRefreshData;
|
||||
this.cancel = cancel;
|
||||
this.dismissView = dismissView;
|
||||
}
|
||||
public BottomSheetLockEvent(boolean cancelable, int delay, boolean shouldRefreshData,
|
||||
boolean cancel) {
|
||||
this.cancelable = cancelable;
|
||||
this.delay = delay;
|
||||
this.shouldRefreshData = shouldRefreshData;
|
||||
this.cancel = cancel;
|
||||
this.dismissView = true;
|
||||
}
|
||||
|
||||
public BottomSheetLockEvent(boolean cancelable, int delay, boolean shouldRefreshData,
|
||||
boolean cancel, boolean
|
||||
dismissView) {
|
||||
this.cancelable = cancelable;
|
||||
this.delay = delay;
|
||||
this.shouldRefreshData = shouldRefreshData;
|
||||
this.cancel = cancel;
|
||||
this.dismissView = dismissView;
|
||||
}
|
||||
}
|
||||
|
@ -26,28 +26,28 @@ import com.nextcloud.talk.utils.ssl.MagicTrustManager;
|
||||
import java.security.cert.X509Certificate;
|
||||
|
||||
public class CertificateEvent {
|
||||
private final X509Certificate x509Certificate;
|
||||
private final MagicTrustManager magicTrustManager;
|
||||
@Nullable
|
||||
private final SslErrorHandler sslErrorHandler;
|
||||
private final X509Certificate x509Certificate;
|
||||
private final MagicTrustManager magicTrustManager;
|
||||
@Nullable
|
||||
private final SslErrorHandler sslErrorHandler;
|
||||
|
||||
public CertificateEvent(X509Certificate x509Certificate, MagicTrustManager magicTrustManager,
|
||||
@Nullable SslErrorHandler sslErrorHandler) {
|
||||
this.x509Certificate = x509Certificate;
|
||||
this.magicTrustManager = magicTrustManager;
|
||||
this.sslErrorHandler = sslErrorHandler;
|
||||
}
|
||||
public CertificateEvent(X509Certificate x509Certificate, MagicTrustManager magicTrustManager,
|
||||
@Nullable SslErrorHandler sslErrorHandler) {
|
||||
this.x509Certificate = x509Certificate;
|
||||
this.magicTrustManager = magicTrustManager;
|
||||
this.sslErrorHandler = sslErrorHandler;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public SslErrorHandler getSslErrorHandler() {
|
||||
return sslErrorHandler;
|
||||
}
|
||||
@Nullable
|
||||
public SslErrorHandler getSslErrorHandler() {
|
||||
return sslErrorHandler;
|
||||
}
|
||||
|
||||
public X509Certificate getX509Certificate() {
|
||||
return x509Certificate;
|
||||
}
|
||||
public X509Certificate getX509Certificate() {
|
||||
return x509Certificate;
|
||||
}
|
||||
|
||||
public MagicTrustManager getMagicTrustManager() {
|
||||
return magicTrustManager;
|
||||
}
|
||||
public MagicTrustManager getMagicTrustManager() {
|
||||
return magicTrustManager;
|
||||
}
|
||||
}
|
||||
|
@ -24,18 +24,17 @@ import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class EventStatus {
|
||||
private long userId;
|
||||
private EventType eventType;
|
||||
private boolean allGood;
|
||||
private long userId;
|
||||
private EventType eventType;
|
||||
private boolean allGood;
|
||||
|
||||
public EventStatus(long userId, EventType eventType, boolean allGood) {
|
||||
this.userId = userId;
|
||||
this.eventType = eventType;
|
||||
this.allGood = allGood;
|
||||
}
|
||||
|
||||
public enum EventType {
|
||||
PUSH_REGISTRATION, CAPABILITIES_FETCH, SIGNALING_SETTINGS, CONVERSATION_UPDATE, PARTICIPANTS_UPDATE
|
||||
}
|
||||
public EventStatus(long userId, EventType eventType, boolean allGood) {
|
||||
this.userId = userId;
|
||||
this.eventType = eventType;
|
||||
this.allGood = allGood;
|
||||
}
|
||||
|
||||
public enum EventType {
|
||||
PUSH_REGISTRATION, CAPABILITIES_FETCH, SIGNALING_SETTINGS, CONVERSATION_UPDATE, PARTICIPANTS_UPDATE
|
||||
}
|
||||
}
|
||||
|
@ -26,13 +26,14 @@ import org.webrtc.MediaStream;
|
||||
|
||||
@Data
|
||||
public class MediaStreamEvent {
|
||||
private final MediaStream mediaStream;
|
||||
private final String session;
|
||||
private final String videoStreamType;
|
||||
private final MediaStream mediaStream;
|
||||
private final String session;
|
||||
private final String videoStreamType;
|
||||
|
||||
public MediaStreamEvent(@Nullable MediaStream mediaStream, String session, String videoStreamType) {
|
||||
this.mediaStream = mediaStream;
|
||||
this.session = session;
|
||||
this.videoStreamType = videoStreamType;
|
||||
}
|
||||
public MediaStreamEvent(@Nullable MediaStream mediaStream, String session,
|
||||
String videoStreamType) {
|
||||
this.mediaStream = mediaStream;
|
||||
this.session = session;
|
||||
this.videoStreamType = videoStreamType;
|
||||
}
|
||||
}
|
||||
|
@ -25,9 +25,9 @@ import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class MoreMenuClickEvent {
|
||||
private final Conversation conversation;
|
||||
private final Conversation conversation;
|
||||
|
||||
public MoreMenuClickEvent(Conversation conversation) {
|
||||
this.conversation = conversation;
|
||||
}
|
||||
public MoreMenuClickEvent(Conversation conversation) {
|
||||
this.conversation = conversation;
|
||||
}
|
||||
}
|
||||
|
@ -24,13 +24,13 @@ import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class NetworkEvent {
|
||||
public enum NetworkConnectionEvent {
|
||||
NETWORK_CONNECTED, NETWORK_DISCONNECTED
|
||||
}
|
||||
private final NetworkConnectionEvent networkConnectionEvent;
|
||||
|
||||
private final NetworkConnectionEvent networkConnectionEvent;
|
||||
public NetworkEvent(NetworkConnectionEvent networkConnectionEvent) {
|
||||
this.networkConnectionEvent = networkConnectionEvent;
|
||||
}
|
||||
|
||||
public NetworkEvent(NetworkConnectionEvent networkConnectionEvent) {
|
||||
this.networkConnectionEvent = networkConnectionEvent;
|
||||
}
|
||||
public enum NetworkConnectionEvent {
|
||||
NETWORK_CONNECTED, NETWORK_DISCONNECTED
|
||||
}
|
||||
}
|
||||
|
@ -25,22 +25,23 @@ import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class PeerConnectionEvent {
|
||||
private final PeerConnectionEventType peerConnectionEventType;
|
||||
private final String sessionId;
|
||||
private final String nick;
|
||||
private final Boolean changeValue;
|
||||
private final String videoStreamType;
|
||||
private final PeerConnectionEventType peerConnectionEventType;
|
||||
private final String sessionId;
|
||||
private final String nick;
|
||||
private final Boolean changeValue;
|
||||
private final String videoStreamType;
|
||||
|
||||
public PeerConnectionEvent(PeerConnectionEventType peerConnectionEventType, @Nullable String sessionId,
|
||||
@Nullable String nick, Boolean changeValue, @Nullable String videoStreamType) {
|
||||
this.peerConnectionEventType = peerConnectionEventType;
|
||||
this.nick = nick;
|
||||
this.changeValue = changeValue;
|
||||
this.sessionId = sessionId;
|
||||
this.videoStreamType = videoStreamType;
|
||||
}
|
||||
public PeerConnectionEvent(PeerConnectionEventType peerConnectionEventType,
|
||||
@Nullable String sessionId,
|
||||
@Nullable String nick, Boolean changeValue, @Nullable String videoStreamType) {
|
||||
this.peerConnectionEventType = peerConnectionEventType;
|
||||
this.nick = nick;
|
||||
this.changeValue = changeValue;
|
||||
this.sessionId = sessionId;
|
||||
this.videoStreamType = videoStreamType;
|
||||
}
|
||||
|
||||
public enum PeerConnectionEventType {
|
||||
PEER_CONNECTED, PEER_CLOSED, SENSOR_FAR, SENSOR_NEAR, NICK_CHANGE, AUDIO_CHANGE, VIDEO_CHANGE, PUBLISHER_FAILED
|
||||
}
|
||||
public enum PeerConnectionEventType {
|
||||
PEER_CONNECTED, PEER_CLOSED, SENSOR_FAR, SENSOR_NEAR, NICK_CHANGE, AUDIO_CHANGE, VIDEO_CHANGE, PUBLISHER_FAILED
|
||||
}
|
||||
}
|
||||
|
@ -27,20 +27,21 @@ import org.webrtc.SessionDescription;
|
||||
|
||||
@Data
|
||||
public class SessionDescriptionSendEvent {
|
||||
@Nullable
|
||||
private final SessionDescription sessionDescription;
|
||||
private final String peerId;
|
||||
private final String type;
|
||||
@Nullable
|
||||
private final NCIceCandidate ncIceCandidate;
|
||||
private final String videoStreamType;
|
||||
@Nullable
|
||||
private final SessionDescription sessionDescription;
|
||||
private final String peerId;
|
||||
private final String type;
|
||||
@Nullable
|
||||
private final NCIceCandidate ncIceCandidate;
|
||||
private final String videoStreamType;
|
||||
|
||||
public SessionDescriptionSendEvent(@Nullable SessionDescription sessionDescription, String peerId, String type,
|
||||
@Nullable NCIceCandidate ncIceCandidate, @Nullable String videoStreamType) {
|
||||
this.sessionDescription = sessionDescription;
|
||||
this.peerId = peerId;
|
||||
this.type = type;
|
||||
this.ncIceCandidate = ncIceCandidate;
|
||||
this.videoStreamType = videoStreamType;
|
||||
}
|
||||
public SessionDescriptionSendEvent(@Nullable SessionDescription sessionDescription, String peerId,
|
||||
String type,
|
||||
@Nullable NCIceCandidate ncIceCandidate, @Nullable String videoStreamType) {
|
||||
this.sessionDescription = sessionDescription;
|
||||
this.peerId = peerId;
|
||||
this.type = type;
|
||||
this.ncIceCandidate = ncIceCandidate;
|
||||
this.videoStreamType = videoStreamType;
|
||||
}
|
||||
}
|
||||
|
@ -24,5 +24,5 @@ import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class UserMentionClickEvent {
|
||||
public final String userId;
|
||||
public final String userId;
|
||||
}
|
||||
|
@ -26,7 +26,7 @@ import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class WebSocketCommunicationEvent {
|
||||
public final String type;
|
||||
@Nullable
|
||||
public final HashMap<String, String> hashMap;
|
||||
public final String type;
|
||||
@Nullable
|
||||
public final HashMap<String, String> hashMap;
|
||||
}
|
@ -22,6 +22,6 @@ package com.nextcloud.talk.interfaces
|
||||
|
||||
interface ClosedInterface {
|
||||
|
||||
val isGooglePlayServicesAvailable: Boolean
|
||||
fun providerInstallerInstallIfNeededAsync()
|
||||
val isGooglePlayServicesAvailable: Boolean
|
||||
fun providerInstallerInstallIfNeededAsync()
|
||||
}
|
||||
|
@ -23,5 +23,8 @@ package com.nextcloud.talk.interfaces
|
||||
import android.os.Bundle
|
||||
|
||||
interface ConversationMenuInterface {
|
||||
fun openLovelyDialogWithIdAndBundle(dialogId: Int, bundle: Bundle)
|
||||
fun openLovelyDialogWithIdAndBundle(
|
||||
dialogId: Int,
|
||||
bundle: Bundle
|
||||
)
|
||||
}
|
||||
|
@ -21,7 +21,7 @@
|
||||
package com.nextcloud.talk.interfaces
|
||||
|
||||
interface SelectionInterface {
|
||||
fun toggleBrowserItemSelection(path: String)
|
||||
fun toggleBrowserItemSelection(path: String)
|
||||
|
||||
fun isPathSelected(path: String): Boolean
|
||||
fun isPathSelected(path: String): Boolean
|
||||
}
|
||||
|
@ -30,12 +30,12 @@ import androidx.work.Worker;
|
||||
import androidx.work.WorkerParameters;
|
||||
import autodagger.AutoInjector;
|
||||
import com.bluelinelabs.logansquare.LoganSquare;
|
||||
import com.nextcloud.talk.models.json.generic.GenericOverall;
|
||||
import com.nextcloud.talk.models.json.push.PushConfigurationState;
|
||||
import com.nextcloud.talk.R;
|
||||
import com.nextcloud.talk.api.NcApi;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.models.json.generic.GenericOverall;
|
||||
import com.nextcloud.talk.models.json.push.PushConfigurationState;
|
||||
import com.nextcloud.talk.utils.ApiUtils;
|
||||
import com.nextcloud.talk.utils.database.arbitrarystorage.ArbitraryStorageUtils;
|
||||
import com.nextcloud.talk.utils.database.user.UserUtils;
|
||||
@ -54,196 +54,205 @@ import retrofit2.Retrofit;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class AccountRemovalWorker extends Worker {
|
||||
public static final String TAG = "AccountRemovalWorker";
|
||||
public static final String TAG = "AccountRemovalWorker";
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
@Inject
|
||||
ArbitraryStorageUtils arbitraryStorageUtils;
|
||||
@Inject
|
||||
ArbitraryStorageUtils arbitraryStorageUtils;
|
||||
|
||||
@Inject
|
||||
Retrofit retrofit;
|
||||
@Inject
|
||||
Retrofit retrofit;
|
||||
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
|
||||
NcApi ncApi;
|
||||
NcApi ncApi;
|
||||
|
||||
public AccountRemovalWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
}
|
||||
public AccountRemovalWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
PushConfigurationState pushConfigurationState;
|
||||
String credentials;
|
||||
for (Object userEntityObject : userUtils.getUsersScheduledForDeletion()) {
|
||||
UserEntity userEntity = (UserEntity) userEntityObject;
|
||||
try {
|
||||
if (!TextUtils.isEmpty(userEntity.getPushConfigurationState())) {
|
||||
pushConfigurationState = LoganSquare.parse(userEntity.getPushConfigurationState(),
|
||||
PushConfigurationState.class);
|
||||
PushConfigurationState finalPushConfigurationState = pushConfigurationState;
|
||||
PushConfigurationState pushConfigurationState;
|
||||
String credentials;
|
||||
for (Object userEntityObject : userUtils.getUsersScheduledForDeletion()) {
|
||||
UserEntity userEntity = (UserEntity) userEntityObject;
|
||||
try {
|
||||
if (!TextUtils.isEmpty(userEntity.getPushConfigurationState())) {
|
||||
pushConfigurationState = LoganSquare.parse(userEntity.getPushConfigurationState(),
|
||||
PushConfigurationState.class);
|
||||
PushConfigurationState finalPushConfigurationState = pushConfigurationState;
|
||||
|
||||
credentials = ApiUtils.getCredentials(userEntity.getUsername(), userEntity.getToken());
|
||||
credentials = ApiUtils.getCredentials(userEntity.getUsername(), userEntity.getToken());
|
||||
|
||||
ncApi = retrofit.newBuilder().client(okHttpClient.newBuilder().cookieJar(new
|
||||
JavaNetCookieJar(new CookieManager())).build()).build().create(NcApi.class);
|
||||
ncApi = retrofit.newBuilder().client(okHttpClient.newBuilder().cookieJar(new
|
||||
JavaNetCookieJar(new CookieManager())).build()).build().create(NcApi.class);
|
||||
|
||||
String finalCredentials = credentials;
|
||||
ncApi.unregisterDeviceForNotificationsWithNextcloud(credentials, ApiUtils.getUrlNextcloudPush(userEntity
|
||||
.getBaseUrl()))
|
||||
.blockingSubscribe(new Observer<GenericOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
String finalCredentials = credentials;
|
||||
ncApi.unregisterDeviceForNotificationsWithNextcloud(credentials,
|
||||
ApiUtils.getUrlNextcloudPush(userEntity
|
||||
.getBaseUrl()))
|
||||
.blockingSubscribe(new Observer<GenericOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(GenericOverall genericOverall) {
|
||||
if (genericOverall.getOcs().getMeta().getStatusCode() == 200
|
||||
|| genericOverall.getOcs().getMeta().getStatusCode() == 202) {
|
||||
HashMap<String, String> queryMap = new HashMap<>();
|
||||
queryMap.put("deviceIdentifier", finalPushConfigurationState.getDeviceIdentifier());
|
||||
queryMap.put("userPublicKey", finalPushConfigurationState.getUserPublicKey());
|
||||
queryMap.put("deviceIdentifierSignature",
|
||||
finalPushConfigurationState.getDeviceIdentifierSignature());
|
||||
|
||||
ncApi.unregisterDeviceForNotificationsWithProxy
|
||||
(ApiUtils.getUrlPushProxy(), queryMap)
|
||||
.subscribe(new Observer<Void>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(Void aVoid) {
|
||||
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
||||
String groupName = String.format(getApplicationContext().getResources()
|
||||
.getString(R.string
|
||||
.nc_notification_channel), userEntity.getUserId(), userEntity.getBaseUrl());
|
||||
CRC32 crc32 = new CRC32();
|
||||
crc32.update(groupName.getBytes());
|
||||
NotificationManager notificationManager =
|
||||
(NotificationManager) getApplicationContext().getSystemService
|
||||
(Context.NOTIFICATION_SERVICE);
|
||||
|
||||
if (notificationManager != null) {
|
||||
notificationManager.deleteNotificationChannelGroup(Long
|
||||
.toString(crc32.getValue()));
|
||||
}
|
||||
}
|
||||
|
||||
WebSocketConnectionHelper.deleteExternalSignalingInstanceForUserEntity(userEntity.getId());
|
||||
|
||||
arbitraryStorageUtils.deleteAllEntriesForAccountIdentifier(userEntity.getId()).subscribe(new Observer() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(Object o) {
|
||||
userUtils.deleteUser(userEntity.getId()).subscribe(new CompletableObserver() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
} else {
|
||||
userUtils.deleteUser(userEntity.getId())
|
||||
.subscribe(new CompletableObserver() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
} catch (IOException e) {
|
||||
Log.d(TAG, "Something went wrong while removing job at parsing PushConfigurationState");
|
||||
userUtils.deleteUser(userEntity.getId())
|
||||
.subscribe(new CompletableObserver() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
@Override
|
||||
public void onNext(GenericOverall genericOverall) {
|
||||
if (genericOverall.getOcs().getMeta().getStatusCode() == 200
|
||||
|| genericOverall.getOcs().getMeta().getStatusCode() == 202) {
|
||||
HashMap<String, String> queryMap = new HashMap<>();
|
||||
queryMap.put("deviceIdentifier",
|
||||
finalPushConfigurationState.getDeviceIdentifier());
|
||||
queryMap.put("userPublicKey", finalPushConfigurationState.getUserPublicKey());
|
||||
queryMap.put("deviceIdentifierSignature",
|
||||
finalPushConfigurationState.getDeviceIdentifierSignature());
|
||||
|
||||
ncApi.unregisterDeviceForNotificationsWithProxy
|
||||
(ApiUtils.getUrlPushProxy(), queryMap)
|
||||
.subscribe(new Observer<Void>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(Void aVoid) {
|
||||
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
||||
String groupName =
|
||||
String.format(getApplicationContext().getResources()
|
||||
.getString(R.string
|
||||
.nc_notification_channel), userEntity.getUserId(),
|
||||
userEntity.getBaseUrl());
|
||||
CRC32 crc32 = new CRC32();
|
||||
crc32.update(groupName.getBytes());
|
||||
NotificationManager notificationManager =
|
||||
(NotificationManager) getApplicationContext().getSystemService
|
||||
(Context.NOTIFICATION_SERVICE);
|
||||
|
||||
if (notificationManager != null) {
|
||||
notificationManager.deleteNotificationChannelGroup(Long
|
||||
.toString(crc32.getValue()));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
WebSocketConnectionHelper.deleteExternalSignalingInstanceForUserEntity(
|
||||
userEntity.getId());
|
||||
|
||||
}
|
||||
arbitraryStorageUtils.deleteAllEntriesForAccountIdentifier(
|
||||
userEntity.getId()).subscribe(new Observer() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
}
|
||||
|
||||
}
|
||||
@Override
|
||||
public void onNext(Object o) {
|
||||
userUtils.deleteUser(userEntity.getId())
|
||||
.subscribe(new CompletableObserver() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return Result.success();
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
} else {
|
||||
userUtils.deleteUser(userEntity.getId())
|
||||
.subscribe(new CompletableObserver() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
} catch (IOException e) {
|
||||
Log.d(TAG, "Something went wrong while removing job at parsing PushConfigurationState");
|
||||
userUtils.deleteUser(userEntity.getId())
|
||||
.subscribe(new CompletableObserver() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
return Result.success();
|
||||
}
|
||||
}
|
||||
|
@ -26,10 +26,10 @@ import androidx.work.Data;
|
||||
import androidx.work.Worker;
|
||||
import androidx.work.WorkerParameters;
|
||||
import autodagger.AutoInjector;
|
||||
import com.nextcloud.talk.models.RetrofitBucket;
|
||||
import com.nextcloud.talk.api.NcApi;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.events.EventStatus;
|
||||
import com.nextcloud.talk.models.RetrofitBucket;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.utils.ApiUtils;
|
||||
import com.nextcloud.talk.utils.bundle.BundleKeys;
|
||||
@ -40,50 +40,56 @@ import org.greenrobot.eventbus.EventBus;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class AddParticipantsToConversation extends Worker {
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
|
||||
public AddParticipantsToConversation(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
public AddParticipantsToConversation(@NonNull Context context,
|
||||
@NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
Data data = getInputData();
|
||||
String[] selectedUserIds = data.getStringArray(BundleKeys.INSTANCE.getKEY_SELECTED_USERS());
|
||||
String[] selectedGroupIds = data.getStringArray(BundleKeys.INSTANCE.getKEY_SELECTED_GROUPS());
|
||||
UserEntity user = userUtils.getUserWithInternalId(
|
||||
data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), -1));
|
||||
String conversationToken = data.getString(BundleKeys.INSTANCE.getKEY_TOKEN());
|
||||
String credentials = ApiUtils.getCredentials(user.getUsername(), user.getToken());
|
||||
|
||||
RetrofitBucket retrofitBucket;
|
||||
for (String userId : selectedUserIds) {
|
||||
retrofitBucket =
|
||||
ApiUtils.getRetrofitBucketForAddParticipant(user.getBaseUrl(), conversationToken,
|
||||
userId);
|
||||
|
||||
ncApi.addParticipant(credentials, retrofitBucket.getUrl(), retrofitBucket.getQueryMap())
|
||||
.subscribeOn(Schedulers.io())
|
||||
.blockingSubscribe();
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
Data data = getInputData();
|
||||
String[] selectedUserIds = data.getStringArray(BundleKeys.INSTANCE.getKEY_SELECTED_USERS());
|
||||
String[] selectedGroupIds = data.getStringArray(BundleKeys.INSTANCE.getKEY_SELECTED_GROUPS());
|
||||
UserEntity user = userUtils.getUserWithInternalId(data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), -1));
|
||||
String conversationToken = data.getString(BundleKeys.INSTANCE.getKEY_TOKEN());
|
||||
String credentials = ApiUtils.getCredentials(user.getUsername(), user.getToken());
|
||||
for (String groupId : selectedGroupIds) {
|
||||
retrofitBucket =
|
||||
ApiUtils.getRetrofitBucketForAddGroupParticipant(user.getBaseUrl(), conversationToken,
|
||||
groupId);
|
||||
|
||||
RetrofitBucket retrofitBucket;
|
||||
for (String userId : selectedUserIds) {
|
||||
retrofitBucket = ApiUtils.getRetrofitBucketForAddParticipant(user.getBaseUrl(), conversationToken,
|
||||
userId);
|
||||
|
||||
ncApi.addParticipant(credentials, retrofitBucket.getUrl(), retrofitBucket.getQueryMap())
|
||||
.subscribeOn(Schedulers.io())
|
||||
.blockingSubscribe();
|
||||
}
|
||||
|
||||
for (String groupId : selectedGroupIds) {
|
||||
retrofitBucket = ApiUtils.getRetrofitBucketForAddGroupParticipant(user.getBaseUrl(), conversationToken,
|
||||
groupId);
|
||||
|
||||
ncApi.addParticipant(credentials, retrofitBucket.getUrl(), retrofitBucket.getQueryMap())
|
||||
.subscribeOn(Schedulers.io())
|
||||
.blockingSubscribe();
|
||||
}
|
||||
|
||||
eventBus.post(new EventStatus(user.getId(), EventStatus.EventType.PARTICIPANTS_UPDATE, true));
|
||||
return Result.success();
|
||||
ncApi.addParticipant(credentials, retrofitBucket.getUrl(), retrofitBucket.getQueryMap())
|
||||
.subscribeOn(Schedulers.io())
|
||||
.blockingSubscribe();
|
||||
}
|
||||
|
||||
eventBus.post(new EventStatus(user.getId(), EventStatus.EventType.PARTICIPANTS_UPDATE, true));
|
||||
return Result.success();
|
||||
}
|
||||
}
|
||||
|
@ -28,11 +28,11 @@ import androidx.work.Worker;
|
||||
import androidx.work.WorkerParameters;
|
||||
import autodagger.AutoInjector;
|
||||
import com.bluelinelabs.logansquare.LoganSquare;
|
||||
import com.nextcloud.talk.models.json.capabilities.CapabilitiesOverall;
|
||||
import com.nextcloud.talk.api.NcApi;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.events.EventStatus;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.models.json.capabilities.CapabilitiesOverall;
|
||||
import com.nextcloud.talk.utils.ApiUtils;
|
||||
import com.nextcloud.talk.utils.bundle.BundleKeys;
|
||||
import com.nextcloud.talk.utils.database.user.UserUtils;
|
||||
@ -50,114 +50,116 @@ import retrofit2.Retrofit;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class CapabilitiesWorker extends Worker {
|
||||
public static final String TAG = "CapabilitiesWorker";
|
||||
public static final String TAG = "CapabilitiesWorker";
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
@Inject
|
||||
Retrofit retrofit;
|
||||
@Inject
|
||||
Retrofit retrofit;
|
||||
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
|
||||
NcApi ncApi;
|
||||
NcApi ncApi;
|
||||
|
||||
public CapabilitiesWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
public CapabilitiesWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
}
|
||||
|
||||
private void updateUser(CapabilitiesOverall capabilitiesOverall, UserEntity internalUserEntity) {
|
||||
try {
|
||||
userUtils.createOrUpdateUser(null, null,
|
||||
null, null,
|
||||
null, null, null, internalUserEntity.getId(),
|
||||
LoganSquare.serialize(capabilitiesOverall.getOcs().getData().getCapabilities()), null,
|
||||
null)
|
||||
.blockingSubscribe(new Observer<UserEntity>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(UserEntity userEntity) {
|
||||
eventBus.post(new EventStatus(userEntity.getId(),
|
||||
EventStatus.EventType.CAPABILITIES_FETCH, true));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
eventBus.post(new EventStatus(internalUserEntity.getId(),
|
||||
EventStatus.EventType.CAPABILITIES_FETCH, false));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to create or update user");
|
||||
}
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
Data data = getInputData();
|
||||
|
||||
long internalUserId = data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), -1);
|
||||
|
||||
UserEntity userEntity;
|
||||
List userEntityObjectList = new ArrayList();
|
||||
|
||||
if (internalUserId == -1
|
||||
|| (userEntity = userUtils.getUserWithInternalId(internalUserId)) == null) {
|
||||
userEntityObjectList = userUtils.getUsers();
|
||||
} else {
|
||||
userEntityObjectList.add(userEntity);
|
||||
}
|
||||
|
||||
private void updateUser(CapabilitiesOverall capabilitiesOverall, UserEntity internalUserEntity) {
|
||||
try {
|
||||
userUtils.createOrUpdateUser(null, null,
|
||||
null, null,
|
||||
null, null, null, internalUserEntity.getId(),
|
||||
LoganSquare.serialize(capabilitiesOverall.getOcs().getData().getCapabilities()), null, null)
|
||||
.blockingSubscribe(new Observer<UserEntity>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
for (Object userEntityObject : userEntityObjectList) {
|
||||
UserEntity internalUserEntity = (UserEntity) userEntityObject;
|
||||
|
||||
}
|
||||
ncApi = retrofit.newBuilder().client(okHttpClient.newBuilder().cookieJar(new
|
||||
JavaNetCookieJar(new CookieManager())).build()).build().create(NcApi.class);
|
||||
|
||||
@Override
|
||||
public void onNext(UserEntity userEntity) {
|
||||
eventBus.post(new EventStatus(userEntity.getId(),
|
||||
EventStatus.EventType.CAPABILITIES_FETCH, true));
|
||||
}
|
||||
ncApi.getCapabilities(ApiUtils.getCredentials(internalUserEntity.getUsername(),
|
||||
internalUserEntity.getToken()),
|
||||
ApiUtils.getUrlForCapabilities(internalUserEntity.getBaseUrl()))
|
||||
.retry(3)
|
||||
.blockingSubscribe(new Observer<CapabilitiesOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
eventBus.post(new EventStatus(internalUserEntity.getId(),
|
||||
EventStatus.EventType.CAPABILITIES_FETCH, false));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
@Override
|
||||
public void onNext(CapabilitiesOverall capabilitiesOverall) {
|
||||
updateUser(capabilitiesOverall, internalUserEntity);
|
||||
}
|
||||
|
||||
}
|
||||
});
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to create or update user");
|
||||
}
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
eventBus.post(new EventStatus(internalUserEntity.getId(),
|
||||
EventStatus.EventType.CAPABILITIES_FETCH, false));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
|
||||
Data data = getInputData();
|
||||
|
||||
long internalUserId = data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), -1);
|
||||
|
||||
UserEntity userEntity;
|
||||
List userEntityObjectList = new ArrayList();
|
||||
|
||||
if (internalUserId == -1 || (userEntity = userUtils.getUserWithInternalId(internalUserId)) == null) {
|
||||
userEntityObjectList = userUtils.getUsers();
|
||||
} else {
|
||||
userEntityObjectList.add(userEntity);
|
||||
}
|
||||
|
||||
for (Object userEntityObject : userEntityObjectList) {
|
||||
UserEntity internalUserEntity = (UserEntity) userEntityObject;
|
||||
|
||||
ncApi = retrofit.newBuilder().client(okHttpClient.newBuilder().cookieJar(new
|
||||
JavaNetCookieJar(new CookieManager())).build()).build().create(NcApi.class);
|
||||
|
||||
ncApi.getCapabilities(ApiUtils.getCredentials(internalUserEntity.getUsername(),
|
||||
internalUserEntity.getToken()), ApiUtils.getUrlForCapabilities(internalUserEntity.getBaseUrl()))
|
||||
.retry(3)
|
||||
.blockingSubscribe(new Observer<CapabilitiesOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(CapabilitiesOverall capabilitiesOverall) {
|
||||
updateUser(capabilitiesOverall, internalUserEntity);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
eventBus.post(new EventStatus(internalUserEntity.getId(),
|
||||
EventStatus.EventType.CAPABILITIES_FETCH, false));
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return Result.success();
|
||||
}
|
||||
return Result.success();
|
||||
}
|
||||
}
|
||||
|
@ -26,11 +26,11 @@ import androidx.work.Data;
|
||||
import androidx.work.Worker;
|
||||
import androidx.work.WorkerParameters;
|
||||
import autodagger.AutoInjector;
|
||||
import com.nextcloud.talk.models.json.generic.GenericOverall;
|
||||
import com.nextcloud.talk.api.NcApi;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.events.EventStatus;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.models.json.generic.GenericOverall;
|
||||
import com.nextcloud.talk.utils.ApiUtils;
|
||||
import com.nextcloud.talk.utils.bundle.BundleKeys;
|
||||
import com.nextcloud.talk.utils.database.user.UserUtils;
|
||||
@ -46,70 +46,72 @@ import retrofit2.Retrofit;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class DeleteConversationWorker extends Worker {
|
||||
@Inject
|
||||
Retrofit retrofit;
|
||||
@Inject
|
||||
Retrofit retrofit;
|
||||
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
|
||||
NcApi ncApi;
|
||||
NcApi ncApi;
|
||||
|
||||
public DeleteConversationWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
public DeleteConversationWorker(@NonNull Context context,
|
||||
@NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
Data data = getInputData();
|
||||
long operationUserId = data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), -1);
|
||||
String conversationToken = data.getString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN());
|
||||
UserEntity operationUser = userUtils.getUserWithId(operationUserId);
|
||||
|
||||
if (operationUser != null) {
|
||||
String credentials =
|
||||
ApiUtils.getCredentials(operationUser.getUsername(), operationUser.getToken());
|
||||
ncApi = retrofit.newBuilder().client(okHttpClient.newBuilder().cookieJar(new
|
||||
JavaNetCookieJar(new CookieManager())).build()).build().create(NcApi.class);
|
||||
|
||||
EventStatus eventStatus = new EventStatus(operationUser.getId(),
|
||||
EventStatus.EventType.CONVERSATION_UPDATE, true);
|
||||
|
||||
ncApi.deleteRoom(credentials, ApiUtils.getRoom(operationUser.getBaseUrl(), conversationToken))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.blockingSubscribe(new Observer<GenericOverall>() {
|
||||
Disposable disposable;
|
||||
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
disposable = d;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(GenericOverall genericOverall) {
|
||||
eventBus.postSticky(eventStatus);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
disposable.dispose();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
Data data = getInputData();
|
||||
long operationUserId = data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), -1);
|
||||
String conversationToken = data.getString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN());
|
||||
UserEntity operationUser = userUtils.getUserWithId(operationUserId);
|
||||
|
||||
if (operationUser != null) {
|
||||
String credentials = ApiUtils.getCredentials(operationUser.getUsername(), operationUser.getToken());
|
||||
ncApi = retrofit.newBuilder().client(okHttpClient.newBuilder().cookieJar(new
|
||||
JavaNetCookieJar(new CookieManager())).build()).build().create(NcApi.class);
|
||||
|
||||
EventStatus eventStatus = new EventStatus(operationUser.getId(),
|
||||
EventStatus.EventType.CONVERSATION_UPDATE, true);
|
||||
|
||||
ncApi.deleteRoom(credentials, ApiUtils.getRoom(operationUser.getBaseUrl(), conversationToken))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.blockingSubscribe(new Observer<GenericOverall>() {
|
||||
Disposable disposable;
|
||||
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
disposable = d;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(GenericOverall genericOverall) {
|
||||
eventBus.postSticky(eventStatus);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
disposable.dispose();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return Result.success();
|
||||
}
|
||||
return Result.success();
|
||||
}
|
||||
}
|
||||
|
@ -26,11 +26,11 @@ import androidx.work.Data;
|
||||
import androidx.work.Worker;
|
||||
import androidx.work.WorkerParameters;
|
||||
import autodagger.AutoInjector;
|
||||
import com.nextcloud.talk.models.json.generic.GenericOverall;
|
||||
import com.nextcloud.talk.api.NcApi;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.events.EventStatus;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.models.json.generic.GenericOverall;
|
||||
import com.nextcloud.talk.utils.ApiUtils;
|
||||
import com.nextcloud.talk.utils.bundle.BundleKeys;
|
||||
import com.nextcloud.talk.utils.database.user.UserUtils;
|
||||
@ -46,70 +46,72 @@ import retrofit2.Retrofit;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class LeaveConversationWorker extends Worker {
|
||||
@Inject
|
||||
Retrofit retrofit;
|
||||
@Inject
|
||||
Retrofit retrofit;
|
||||
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
@Inject
|
||||
OkHttpClient okHttpClient;
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
|
||||
NcApi ncApi;
|
||||
NcApi ncApi;
|
||||
|
||||
public LeaveConversationWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
public LeaveConversationWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
Data data = getInputData();
|
||||
long operationUserId = data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), -1);
|
||||
String conversationToken = data.getString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN());
|
||||
UserEntity operationUser = userUtils.getUserWithId(operationUserId);
|
||||
|
||||
if (operationUser != null) {
|
||||
String credentials =
|
||||
ApiUtils.getCredentials(operationUser.getUsername(), operationUser.getToken());
|
||||
ncApi = retrofit.newBuilder().client(okHttpClient.newBuilder().cookieJar(new
|
||||
JavaNetCookieJar(new CookieManager())).build()).build().create(NcApi.class);
|
||||
|
||||
EventStatus eventStatus = new EventStatus(operationUser.getId(),
|
||||
EventStatus.EventType.CONVERSATION_UPDATE, true);
|
||||
|
||||
ncApi.removeSelfFromRoom(credentials,
|
||||
ApiUtils.getUrlForRemoveSelfFromRoom(operationUser.getBaseUrl(), conversationToken))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.blockingSubscribe(new Observer<GenericOverall>() {
|
||||
Disposable disposable;
|
||||
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
disposable = d;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(GenericOverall genericOverall) {
|
||||
eventBus.postSticky(eventStatus);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
disposable.dispose();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
Data data = getInputData();
|
||||
long operationUserId = data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), -1);
|
||||
String conversationToken = data.getString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN());
|
||||
UserEntity operationUser = userUtils.getUserWithId(operationUserId);
|
||||
|
||||
if (operationUser != null) {
|
||||
String credentials = ApiUtils.getCredentials(operationUser.getUsername(), operationUser.getToken());
|
||||
ncApi = retrofit.newBuilder().client(okHttpClient.newBuilder().cookieJar(new
|
||||
JavaNetCookieJar(new CookieManager())).build()).build().create(NcApi.class);
|
||||
|
||||
EventStatus eventStatus = new EventStatus(operationUser.getId(),
|
||||
EventStatus.EventType.CONVERSATION_UPDATE, true);
|
||||
|
||||
ncApi.removeSelfFromRoom(credentials, ApiUtils.getUrlForRemoveSelfFromRoom(operationUser.getBaseUrl(), conversationToken))
|
||||
.subscribeOn(Schedulers.io())
|
||||
.blockingSubscribe(new Observer<GenericOverall>() {
|
||||
Disposable disposable;
|
||||
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
disposable = d;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(GenericOverall genericOverall) {
|
||||
eventBus.postSticky(eventStatus);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
disposable.dispose();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return Result.success();
|
||||
}
|
||||
return Result.success();
|
||||
}
|
||||
}
|
||||
|
@ -27,19 +27,19 @@ import androidx.work.WorkerParameters;
|
||||
import com.nextcloud.talk.utils.PushUtils;
|
||||
|
||||
public class PushRegistrationWorker extends Worker {
|
||||
public static final String TAG = "PushRegistrationWorker";
|
||||
public static final String TAG = "PushRegistrationWorker";
|
||||
|
||||
public PushRegistrationWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
}
|
||||
public PushRegistrationWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
PushUtils pushUtils = new PushUtils();
|
||||
pushUtils.generateRsa2048KeyPair();
|
||||
pushUtils.pushRegistrationToServer();
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
PushUtils pushUtils = new PushUtils();
|
||||
pushUtils.generateRsa2048KeyPair();
|
||||
pushUtils.pushRegistrationToServer();
|
||||
|
||||
return Result.success();
|
||||
}
|
||||
return Result.success();
|
||||
}
|
||||
}
|
||||
|
@ -42,63 +42,64 @@ import javax.inject.Inject;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class ShareOperationWorker extends Worker {
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
private long userId;
|
||||
private UserEntity operationsUser;
|
||||
private String roomToken;
|
||||
private List<String> filesArray = new ArrayList<>();
|
||||
private String credentials;
|
||||
private String baseUrl;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
private long userId;
|
||||
private UserEntity operationsUser;
|
||||
private String roomToken;
|
||||
private List<String> filesArray = new ArrayList<>();
|
||||
private String credentials;
|
||||
private String baseUrl;
|
||||
|
||||
public ShareOperationWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
Data data = workerParams.getInputData();
|
||||
userId = data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), 0);
|
||||
roomToken = data.getString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN());
|
||||
Collections.addAll(filesArray, data.getStringArray(BundleKeys.INSTANCE.getKEY_FILE_PATHS()));
|
||||
operationsUser = userUtils.getUserWithId(userId);
|
||||
credentials = ApiUtils.getCredentials(operationsUser.getUsername(), operationsUser.getToken());
|
||||
baseUrl = operationsUser.getBaseUrl();
|
||||
public ShareOperationWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
Data data = workerParams.getInputData();
|
||||
userId = data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), 0);
|
||||
roomToken = data.getString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN());
|
||||
Collections.addAll(filesArray, data.getStringArray(BundleKeys.INSTANCE.getKEY_FILE_PATHS()));
|
||||
operationsUser = userUtils.getUserWithId(userId);
|
||||
credentials = ApiUtils.getCredentials(operationsUser.getUsername(), operationsUser.getToken());
|
||||
baseUrl = operationsUser.getBaseUrl();
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
for (int i = 0; i < filesArray.size(); i++) {
|
||||
ncApi.createRemoteShare(credentials,
|
||||
ApiUtils.getSharingUrl(baseUrl),
|
||||
filesArray.get(i),
|
||||
roomToken,
|
||||
"10")
|
||||
.subscribeOn(Schedulers.io())
|
||||
.blockingSubscribe(new Observer<Void>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(Void aVoid) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
for (int i = 0; i < filesArray.size(); i++) {
|
||||
ncApi.createRemoteShare(credentials,
|
||||
ApiUtils.getSharingUrl(baseUrl),
|
||||
filesArray.get(i),
|
||||
roomToken,
|
||||
"10")
|
||||
.subscribeOn(Schedulers.io())
|
||||
.blockingSubscribe(new Observer<Void>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(Void aVoid) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return Result.success();
|
||||
}
|
||||
return Result.success();
|
||||
}
|
||||
}
|
||||
|
@ -30,12 +30,12 @@ import androidx.work.Worker;
|
||||
import androidx.work.WorkerParameters;
|
||||
import autodagger.AutoInjector;
|
||||
import com.bluelinelabs.logansquare.LoganSquare;
|
||||
import com.nextcloud.talk.models.ExternalSignalingServer;
|
||||
import com.nextcloud.talk.models.json.signaling.settings.SignalingSettingsOverall;
|
||||
import com.nextcloud.talk.api.NcApi;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.events.EventStatus;
|
||||
import com.nextcloud.talk.models.ExternalSignalingServer;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.models.json.signaling.settings.SignalingSettingsOverall;
|
||||
import com.nextcloud.talk.utils.ApiUtils;
|
||||
import com.nextcloud.talk.utils.bundle.BundleKeys;
|
||||
import com.nextcloud.talk.utils.database.user.UserUtils;
|
||||
@ -49,100 +49,112 @@ import org.greenrobot.eventbus.EventBus;
|
||||
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class SignalingSettingsWorker extends Worker {
|
||||
private static final String TAG = "SignalingSettingsJob";
|
||||
private static final String TAG = "SignalingSettingsJob";
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
@Inject
|
||||
NcApi ncApi;
|
||||
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
@Inject
|
||||
EventBus eventBus;
|
||||
|
||||
public SignalingSettingsWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
public SignalingSettingsWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
Data data = getInputData();
|
||||
|
||||
long internalUserId = data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), -1);
|
||||
|
||||
List<UserEntity> userEntityList = new ArrayList<>();
|
||||
UserEntity userEntity;
|
||||
if (internalUserId == -1
|
||||
|| (userEntity = userUtils.getUserWithInternalId(internalUserId)) == null) {
|
||||
userEntityList = userUtils.getUsers();
|
||||
} else {
|
||||
userEntityList.add(userEntity);
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
for (int i = 0; i < userEntityList.size(); i++) {
|
||||
userEntity = userEntityList.get(i);
|
||||
UserEntity finalUserEntity = userEntity;
|
||||
ncApi.getSignalingSettings(
|
||||
ApiUtils.getCredentials(userEntity.getUsername(), userEntity.getToken()),
|
||||
ApiUtils.getUrlForSignalingSettings(userEntity.getBaseUrl()))
|
||||
.blockingSubscribe(new Observer<SignalingSettingsOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
Data data = getInputData();
|
||||
}
|
||||
|
||||
long internalUserId = data.getLong(BundleKeys.INSTANCE.getKEY_INTERNAL_USER_ID(), -1);
|
||||
@Override
|
||||
public void onNext(SignalingSettingsOverall signalingSettingsOverall) {
|
||||
ExternalSignalingServer externalSignalingServer;
|
||||
externalSignalingServer = new ExternalSignalingServer();
|
||||
externalSignalingServer.setExternalSignalingServer(
|
||||
signalingSettingsOverall.getOcs().getSettings().getExternalSignalingServer());
|
||||
externalSignalingServer.setExternalSignalingTicket(
|
||||
signalingSettingsOverall.getOcs().getSettings().getExternalSignalingTicket());
|
||||
|
||||
List<UserEntity> userEntityList = new ArrayList<>();
|
||||
UserEntity userEntity;
|
||||
if (internalUserId == -1 || (userEntity = userUtils.getUserWithInternalId(internalUserId)) == null) {
|
||||
userEntityList = userUtils.getUsers();
|
||||
} else {
|
||||
userEntityList.add(userEntity);
|
||||
}
|
||||
try {
|
||||
userUtils.createOrUpdateUser(null, null, null, null, null,
|
||||
null, null, finalUserEntity.getId(), null, null,
|
||||
LoganSquare.serialize(externalSignalingServer))
|
||||
.subscribe(new Observer<UserEntity>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
|
||||
for (int i = 0; i < userEntityList.size(); i++) {
|
||||
userEntity = userEntityList.get(i);
|
||||
UserEntity finalUserEntity = userEntity;
|
||||
ncApi.getSignalingSettings(ApiUtils.getCredentials(userEntity.getUsername(), userEntity.getToken()),
|
||||
ApiUtils.getUrlForSignalingSettings(userEntity.getBaseUrl()))
|
||||
.blockingSubscribe(new Observer<SignalingSettingsOverall>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
}
|
||||
|
||||
}
|
||||
@Override
|
||||
public void onNext(UserEntity userEntity) {
|
||||
eventBus.post(new EventStatus(finalUserEntity.getId(),
|
||||
EventStatus.EventType.SIGNALING_SETTINGS, true));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(SignalingSettingsOverall signalingSettingsOverall) {
|
||||
ExternalSignalingServer externalSignalingServer;
|
||||
externalSignalingServer = new ExternalSignalingServer();
|
||||
externalSignalingServer.setExternalSignalingServer(signalingSettingsOverall.getOcs().getSettings().getExternalSignalingServer());
|
||||
externalSignalingServer.setExternalSignalingTicket(signalingSettingsOverall.getOcs().getSettings().getExternalSignalingTicket());
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
eventBus.post(new EventStatus(finalUserEntity.getId(),
|
||||
EventStatus.EventType.SIGNALING_SETTINGS, false));
|
||||
}
|
||||
|
||||
try {
|
||||
userUtils.createOrUpdateUser(null, null, null, null, null,
|
||||
null, null, finalUserEntity.getId(), null, null, LoganSquare.serialize(externalSignalingServer))
|
||||
.subscribe(new Observer<UserEntity>() {
|
||||
@Override
|
||||
public void onSubscribe(Disposable d) {
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNext(UserEntity userEntity) {
|
||||
eventBus.post(new EventStatus(finalUserEntity.getId(), EventStatus.EventType.SIGNALING_SETTINGS, true));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
eventBus.post(new EventStatus(finalUserEntity.getId(), EventStatus.EventType.SIGNALING_SETTINGS, false));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to serialize external signaling server");
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
eventBus.post(new EventStatus(finalUserEntity.getId(), EventStatus.EventType.SIGNALING_SETTINGS, false));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to serialize external signaling server");
|
||||
}
|
||||
}
|
||||
|
||||
OneTimeWorkRequest websocketConnectionsWorker = new OneTimeWorkRequest.Builder(WebsocketConnectionsWorker.class).build();
|
||||
WorkManager.getInstance().enqueue(websocketConnectionsWorker);
|
||||
@Override
|
||||
public void onError(Throwable e) {
|
||||
eventBus.post(
|
||||
new EventStatus(finalUserEntity.getId(), EventStatus.EventType.SIGNALING_SETTINGS,
|
||||
false));
|
||||
}
|
||||
|
||||
return Result.success();
|
||||
@Override
|
||||
public void onComplete() {
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
OneTimeWorkRequest websocketConnectionsWorker =
|
||||
new OneTimeWorkRequest.Builder(WebsocketConnectionsWorker.class).build();
|
||||
WorkManager.getInstance().enqueue(websocketConnectionsWorker);
|
||||
|
||||
return Result.success();
|
||||
}
|
||||
}
|
||||
|
@ -29,8 +29,8 @@ import androidx.work.Worker;
|
||||
import androidx.work.WorkerParameters;
|
||||
import autodagger.AutoInjector;
|
||||
import com.bluelinelabs.logansquare.LoganSquare;
|
||||
import com.nextcloud.talk.models.ExternalSignalingServer;
|
||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
||||
import com.nextcloud.talk.models.ExternalSignalingServer;
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import com.nextcloud.talk.utils.database.user.UserUtils;
|
||||
import com.nextcloud.talk.webrtc.WebSocketConnectionHelper;
|
||||
@ -41,43 +41,47 @@ import javax.inject.Inject;
|
||||
@AutoInjector(NextcloudTalkApplication.class)
|
||||
public class WebsocketConnectionsWorker extends Worker {
|
||||
|
||||
private static final String TAG = "WebsocketConnectionsWorker";
|
||||
private static final String TAG = "WebsocketConnectionsWorker";
|
||||
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
@Inject
|
||||
UserUtils userUtils;
|
||||
|
||||
public WebsocketConnectionsWorker(@NonNull Context context, @NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
}
|
||||
public WebsocketConnectionsWorker(@NonNull Context context,
|
||||
@NonNull WorkerParameters workerParams) {
|
||||
super(context, workerParams);
|
||||
}
|
||||
|
||||
@SuppressLint("LongLogTag")
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||
@SuppressLint("LongLogTag")
|
||||
@NonNull
|
||||
@Override
|
||||
public Result doWork() {
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getComponentApplication()
|
||||
.inject(this);
|
||||
|
||||
List<UserEntity> userEntityList = userUtils.getUsers();
|
||||
UserEntity userEntity;
|
||||
ExternalSignalingServer externalSignalingServer;
|
||||
WebSocketConnectionHelper webSocketConnectionHelper = new WebSocketConnectionHelper();
|
||||
for (int i = 0; i < userEntityList.size(); i++) {
|
||||
userEntity = userEntityList.get(i);
|
||||
if (!TextUtils.isEmpty(userEntity.getExternalSignalingServer())) {
|
||||
try {
|
||||
externalSignalingServer = LoganSquare.parse(userEntity.getExternalSignalingServer(), ExternalSignalingServer.class);
|
||||
if (!TextUtils.isEmpty(externalSignalingServer.getExternalSignalingServer()) &&
|
||||
!TextUtils.isEmpty(externalSignalingServer.getExternalSignalingTicket())) {
|
||||
WebSocketConnectionHelper.getExternalSignalingInstanceForServer(
|
||||
externalSignalingServer.getExternalSignalingServer(),
|
||||
userEntity, externalSignalingServer.getExternalSignalingTicket(),
|
||||
false);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to parse external signaling server");
|
||||
}
|
||||
}
|
||||
List<UserEntity> userEntityList = userUtils.getUsers();
|
||||
UserEntity userEntity;
|
||||
ExternalSignalingServer externalSignalingServer;
|
||||
WebSocketConnectionHelper webSocketConnectionHelper = new WebSocketConnectionHelper();
|
||||
for (int i = 0; i < userEntityList.size(); i++) {
|
||||
userEntity = userEntityList.get(i);
|
||||
if (!TextUtils.isEmpty(userEntity.getExternalSignalingServer())) {
|
||||
try {
|
||||
externalSignalingServer = LoganSquare.parse(userEntity.getExternalSignalingServer(),
|
||||
ExternalSignalingServer.class);
|
||||
if (!TextUtils.isEmpty(externalSignalingServer.getExternalSignalingServer()) &&
|
||||
!TextUtils.isEmpty(externalSignalingServer.getExternalSignalingTicket())) {
|
||||
WebSocketConnectionHelper.getExternalSignalingInstanceForServer(
|
||||
externalSignalingServer.getExternalSignalingServer(),
|
||||
userEntity, externalSignalingServer.getExternalSignalingTicket(),
|
||||
false);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to parse external signaling server");
|
||||
}
|
||||
|
||||
return Result.success();
|
||||
}
|
||||
}
|
||||
|
||||
return Result.success();
|
||||
}
|
||||
}
|
||||
|
@ -29,8 +29,8 @@ import org.parceler.Parcel;
|
||||
@Parcel
|
||||
@JsonObject
|
||||
public class ExternalSignalingServer {
|
||||
@JsonField(name = "externalSignalingServer")
|
||||
String externalSignalingServer;
|
||||
@JsonField(name = "externalSignalingTicket")
|
||||
String externalSignalingTicket;
|
||||
@JsonField(name = "externalSignalingServer")
|
||||
String externalSignalingServer;
|
||||
@JsonField(name = "externalSignalingTicket")
|
||||
String externalSignalingTicket;
|
||||
}
|
||||
|
@ -25,14 +25,14 @@ import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class ImportAccount {
|
||||
public String username;
|
||||
@Nullable
|
||||
public String token;
|
||||
public String baseUrl;
|
||||
public String username;
|
||||
@Nullable
|
||||
public String token;
|
||||
public String baseUrl;
|
||||
|
||||
public ImportAccount(String username, @Nullable String token, String baseUrl) {
|
||||
this.username = username;
|
||||
this.token = token;
|
||||
this.baseUrl = baseUrl;
|
||||
}
|
||||
public ImportAccount(String username, @Nullable String token, String baseUrl) {
|
||||
this.username = username;
|
||||
this.token = token;
|
||||
this.baseUrl = baseUrl;
|
||||
}
|
||||
}
|
||||
|
@ -26,7 +26,7 @@ import org.parceler.Parcel;
|
||||
@Parcel
|
||||
@Data
|
||||
public class LoginData {
|
||||
String serverUrl;
|
||||
String username;
|
||||
String token;
|
||||
String serverUrl;
|
||||
String username;
|
||||
String token;
|
||||
}
|
||||
|
@ -26,6 +26,6 @@ import org.parceler.Parcel;
|
||||
@Parcel
|
||||
@Data
|
||||
public class RetrofitBucket {
|
||||
public String url;
|
||||
public Map<String, String> queryMap;
|
||||
public String url;
|
||||
public Map<String, String> queryMap;
|
||||
}
|
||||
|
@ -32,9 +32,9 @@ import org.parceler.Parcel;
|
||||
@JsonObject
|
||||
@Data
|
||||
public class RingtoneSettings {
|
||||
@JsonField(name = "ringtoneUri", typeConverter = UriTypeConverter.class)
|
||||
@Nullable
|
||||
Uri ringtoneUri;
|
||||
@JsonField(name = "ringtoneName")
|
||||
String ringtoneName;
|
||||
@JsonField(name = "ringtoneUri", typeConverter = UriTypeConverter.class)
|
||||
@Nullable
|
||||
Uri ringtoneUri;
|
||||
@JsonField(name = "ringtoneName")
|
||||
String ringtoneName;
|
||||
}
|
||||
|
@ -20,7 +20,6 @@
|
||||
|
||||
package com.nextcloud.talk.models;
|
||||
|
||||
|
||||
import com.nextcloud.talk.models.database.UserEntity;
|
||||
import lombok.Data;
|
||||
import org.parceler.Parcel;
|
||||
@ -28,6 +27,6 @@ import org.parceler.Parcel;
|
||||
@Data
|
||||
@Parcel
|
||||
public class SignatureVerification {
|
||||
boolean signatureValid;
|
||||
UserEntity userEntity;
|
||||
boolean signatureValid;
|
||||
UserEntity userEntity;
|
||||
}
|
||||
|
@ -28,12 +28,12 @@ import java.io.Serializable;
|
||||
|
||||
@Entity
|
||||
public interface ArbitraryStorage extends Parcelable, Persistable, Serializable {
|
||||
@Key
|
||||
long getAccountIdentifier();
|
||||
@Key
|
||||
long getAccountIdentifier();
|
||||
|
||||
String getKey();
|
||||
String getKey();
|
||||
|
||||
String getObject();
|
||||
String getObject();
|
||||
|
||||
String getValue();
|
||||
String getValue();
|
||||
}
|
||||
|
@ -33,98 +33,103 @@ import java.util.HashMap;
|
||||
|
||||
@Entity
|
||||
public interface User extends Parcelable, Persistable, Serializable {
|
||||
String TAG = "UserEntity";
|
||||
String TAG = "UserEntity";
|
||||
|
||||
@Key
|
||||
@Generated
|
||||
long getId();
|
||||
@Key
|
||||
@Generated
|
||||
long getId();
|
||||
|
||||
String getUserId();
|
||||
String getUserId();
|
||||
|
||||
String getUsername();
|
||||
String getUsername();
|
||||
|
||||
String getBaseUrl();
|
||||
String getBaseUrl();
|
||||
|
||||
String getToken();
|
||||
String getToken();
|
||||
|
||||
String getDisplayName();
|
||||
String getDisplayName();
|
||||
|
||||
String getPushConfigurationState();
|
||||
String getPushConfigurationState();
|
||||
|
||||
String getCapabilities();
|
||||
String getCapabilities();
|
||||
|
||||
String getClientCertificate();
|
||||
String getClientCertificate();
|
||||
|
||||
String getExternalSignalingServer();
|
||||
String getExternalSignalingServer();
|
||||
|
||||
boolean getCurrent();
|
||||
boolean getCurrent();
|
||||
|
||||
boolean getScheduledForDeletion();
|
||||
boolean getScheduledForDeletion();
|
||||
|
||||
default boolean hasNotificationsCapability(String capabilityName) {
|
||||
if (getCapabilities() != null) {
|
||||
try {
|
||||
Capabilities capabilities = LoganSquare.parse(getCapabilities(), Capabilities.class);
|
||||
if (capabilities.getNotificationsCapability() != null && capabilities.getNotificationsCapability().getFeatures() != null) {
|
||||
return capabilities.getSpreedCapability().getFeatures().contains(capabilityName);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to get capabilities for the user");
|
||||
}
|
||||
default boolean hasNotificationsCapability(String capabilityName) {
|
||||
if (getCapabilities() != null) {
|
||||
try {
|
||||
Capabilities capabilities = LoganSquare.parse(getCapabilities(), Capabilities.class);
|
||||
if (capabilities.getNotificationsCapability() != null
|
||||
&& capabilities.getNotificationsCapability().getFeatures() != null) {
|
||||
return capabilities.getSpreedCapability().getFeatures().contains(capabilityName);
|
||||
}
|
||||
return false;
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to get capabilities for the user");
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
default boolean hasExternalCapability(String capabilityName) {
|
||||
if (getCapabilities() != null) {
|
||||
try {
|
||||
Capabilities capabilities = LoganSquare.parse(getCapabilities(), Capabilities.class);
|
||||
if (capabilities.getExternalCapability() != null && capabilities.getExternalCapability().containsKey("v1")) {
|
||||
return capabilities.getExternalCapability().get("v1").contains("capabilityName");
|
||||
}
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to get capabilities for the user");
|
||||
}
|
||||
default boolean hasExternalCapability(String capabilityName) {
|
||||
if (getCapabilities() != null) {
|
||||
try {
|
||||
Capabilities capabilities = LoganSquare.parse(getCapabilities(), Capabilities.class);
|
||||
if (capabilities.getExternalCapability() != null && capabilities.getExternalCapability()
|
||||
.containsKey("v1")) {
|
||||
return capabilities.getExternalCapability().get("v1").contains("capabilityName");
|
||||
}
|
||||
return false;
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to get capabilities for the user");
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
default boolean hasSpreedFeatureCapability(String capabilityName) {
|
||||
if (getCapabilities() != null) {
|
||||
try {
|
||||
Capabilities capabilities = LoganSquare.parse(getCapabilities(), Capabilities.class);
|
||||
if (capabilities != null && capabilities.getSpreedCapability() != null &&
|
||||
capabilities.getSpreedCapability().getFeatures() != null) {
|
||||
return capabilities.getSpreedCapability().getFeatures().contains(capabilityName);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to get capabilities for the user");
|
||||
}
|
||||
default boolean hasSpreedFeatureCapability(String capabilityName) {
|
||||
if (getCapabilities() != null) {
|
||||
try {
|
||||
Capabilities capabilities = LoganSquare.parse(getCapabilities(), Capabilities.class);
|
||||
if (capabilities != null && capabilities.getSpreedCapability() != null &&
|
||||
capabilities.getSpreedCapability().getFeatures() != null) {
|
||||
return capabilities.getSpreedCapability().getFeatures().contains(capabilityName);
|
||||
}
|
||||
return false;
|
||||
} catch (IOException e) {
|
||||
Log.e(TAG, "Failed to get capabilities for the user");
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
default int getMessageMaxLength() {
|
||||
if (getCapabilities() != null) {
|
||||
Capabilities capabilities = null;
|
||||
try {
|
||||
capabilities = LoganSquare.parse(getCapabilities(), Capabilities.class);
|
||||
if (capabilities != null && capabilities.getSpreedCapability() != null && capabilities.getSpreedCapability().getConfig() != null
|
||||
&& capabilities.getSpreedCapability().getConfig().containsKey("chat")) {
|
||||
HashMap<String, String> chatConfigHashMap = capabilities.getSpreedCapability().getConfig().get("chat");
|
||||
if (chatConfigHashMap != null && chatConfigHashMap.containsKey("max-length")) {
|
||||
int chatSize = Integer.parseInt(chatConfigHashMap.get("max-length"));
|
||||
if (chatSize > 0) {
|
||||
return chatSize;
|
||||
} else {
|
||||
return 1000;
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
default int getMessageMaxLength() {
|
||||
if (getCapabilities() != null) {
|
||||
Capabilities capabilities = null;
|
||||
try {
|
||||
capabilities = LoganSquare.parse(getCapabilities(), Capabilities.class);
|
||||
if (capabilities != null
|
||||
&& capabilities.getSpreedCapability() != null
|
||||
&& capabilities.getSpreedCapability().getConfig() != null
|
||||
&& capabilities.getSpreedCapability().getConfig().containsKey("chat")) {
|
||||
HashMap<String, String> chatConfigHashMap =
|
||||
capabilities.getSpreedCapability().getConfig().get("chat");
|
||||
if (chatConfigHashMap != null && chatConfigHashMap.containsKey("max-length")) {
|
||||
int chatSize = Integer.parseInt(chatConfigHashMap.get("max-length"));
|
||||
if (chatSize > 0) {
|
||||
return chatSize;
|
||||
} else {
|
||||
return 1000;
|
||||
}
|
||||
}
|
||||
}
|
||||
return 1000;
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
return 1000;
|
||||
}
|
||||
}
|
||||
|
@ -31,6 +31,6 @@ import org.parceler.Parcel;
|
||||
@Data
|
||||
@JsonObject
|
||||
public class AutocompleteOCS extends GenericOCS {
|
||||
@JsonField(name = "data")
|
||||
List<AutocompleteUser> data;
|
||||
@JsonField(name = "data")
|
||||
List<AutocompleteUser> data;
|
||||
}
|
||||
|
@ -29,6 +29,6 @@ import org.parceler.Parcel;
|
||||
@Data
|
||||
@JsonObject
|
||||
public class AutocompleteOverall {
|
||||
@JsonField(name = "ocs")
|
||||
AutocompleteOCS ocs;
|
||||
@JsonField(name = "ocs")
|
||||
AutocompleteOCS ocs;
|
||||
}
|
||||
|
@ -29,12 +29,12 @@ import org.parceler.Parcel;
|
||||
@Data
|
||||
@JsonObject
|
||||
public class AutocompleteUser {
|
||||
@JsonField(name = "id")
|
||||
String id;
|
||||
@JsonField(name = "id")
|
||||
String id;
|
||||
|
||||
@JsonField(name = "label")
|
||||
String label;
|
||||
@JsonField(name = "label")
|
||||
String label;
|
||||
|
||||
@JsonField(name = "source")
|
||||
String source;
|
||||
@JsonField(name = "source")
|
||||
String source;
|
||||
}
|
||||
|
@ -31,15 +31,15 @@ import org.parceler.Parcel;
|
||||
@Data
|
||||
@JsonObject
|
||||
public class Capabilities {
|
||||
@JsonField(name = "spreed")
|
||||
SpreedCapability spreedCapability;
|
||||
@JsonField(name = "spreed")
|
||||
SpreedCapability spreedCapability;
|
||||
|
||||
@JsonField(name = "notifications")
|
||||
NotificationsCapability notificationsCapability;
|
||||
@JsonField(name = "notifications")
|
||||
NotificationsCapability notificationsCapability;
|
||||
|
||||
@JsonField(name = "theming")
|
||||
ThemingCapability themingCapability;
|
||||
@JsonField(name = "theming")
|
||||
ThemingCapability themingCapability;
|
||||
|
||||
@JsonField(name = "external")
|
||||
HashMap<String, List<String>> externalCapability;
|
||||
@JsonField(name = "external")
|
||||
HashMap<String, List<String>> externalCapability;
|
||||
}
|
||||
|
@ -29,6 +29,6 @@ import org.parceler.Parcel;
|
||||
@Data
|
||||
@JsonObject
|
||||
public class CapabilitiesList {
|
||||
@JsonField(name = "capabilities")
|
||||
Capabilities capabilities;
|
||||
@JsonField(name = "capabilities")
|
||||
Capabilities capabilities;
|
||||
}
|
||||
|
@ -29,6 +29,6 @@ import org.parceler.Parcel;
|
||||
@Parcel
|
||||
@JsonObject
|
||||
public class CapabilitiesOCS extends GenericOCS {
|
||||
@JsonField(name = "data")
|
||||
CapabilitiesList data;
|
||||
@JsonField(name = "data")
|
||||
CapabilitiesList data;
|
||||
}
|
||||
|
@ -28,6 +28,6 @@ import org.parceler.Parcel;
|
||||
@Parcel
|
||||
@JsonObject
|
||||
public class CapabilitiesOverall {
|
||||
@JsonField(name = "ocs")
|
||||
CapabilitiesOCS ocs;
|
||||
@JsonField(name = "ocs")
|
||||
CapabilitiesOCS ocs;
|
||||
}
|
||||
|
@ -30,6 +30,6 @@ import org.parceler.Parcel;
|
||||
@Data
|
||||
@JsonObject
|
||||
public class NotificationsCapability {
|
||||
@JsonField(name = "ocs-endpoints")
|
||||
List<String> features;
|
||||
@JsonField(name = "ocs-endpoints")
|
||||
List<String> features;
|
||||
}
|
||||
|
@ -31,9 +31,9 @@ import org.parceler.Parcel;
|
||||
@Data
|
||||
@JsonObject
|
||||
public class SpreedCapability {
|
||||
@JsonField(name = "features")
|
||||
List<String> features;
|
||||
@JsonField(name = "features")
|
||||
List<String> features;
|
||||
|
||||
@JsonField(name = "config")
|
||||
HashMap<String, HashMap<String, String>> config;
|
||||
@JsonField(name = "config")
|
||||
HashMap<String, HashMap<String, String>> config;
|
||||
}
|
||||
|
@ -29,33 +29,33 @@ import org.parceler.Parcel;
|
||||
@Data
|
||||
@JsonObject
|
||||
class ThemingCapability {
|
||||
@JsonField(name = "name")
|
||||
String name;
|
||||
@JsonField(name = "name")
|
||||
String name;
|
||||
|
||||
@JsonField(name = "url")
|
||||
String url;
|
||||
@JsonField(name = "url")
|
||||
String url;
|
||||
|
||||
@JsonField(name = "slogan")
|
||||
String slogan;
|
||||
@JsonField(name = "slogan")
|
||||
String slogan;
|
||||
|
||||
@JsonField(name = "color")
|
||||
String color;
|
||||
@JsonField(name = "color")
|
||||
String color;
|
||||
|
||||
@JsonField(name = "color-text")
|
||||
String colorText;
|
||||
@JsonField(name = "color-text")
|
||||
String colorText;
|
||||
|
||||
@JsonField(name = "color-element")
|
||||
String colorElement;
|
||||
@JsonField(name = "color-element")
|
||||
String colorElement;
|
||||
|
||||
@JsonField(name = "logo")
|
||||
String logo;
|
||||
@JsonField(name = "logo")
|
||||
String logo;
|
||||
|
||||
@JsonField(name = "background")
|
||||
String background;
|
||||
@JsonField(name = "background")
|
||||
String background;
|
||||
|
||||
@JsonField(name = "background-plain")
|
||||
boolean backgroundPlain;
|
||||
@JsonField(name = "background-plain")
|
||||
boolean backgroundPlain;
|
||||
|
||||
@JsonField(name = "background-default")
|
||||
boolean backgroundDefault;
|
||||
@JsonField(name = "background-default")
|
||||
boolean backgroundDefault;
|
||||
}
|
||||
|
@ -45,233 +45,269 @@ import org.parceler.Parcel;
|
||||
@Data
|
||||
@JsonObject
|
||||
public class ChatMessage implements IMessage, MessageContentType, MessageContentType.Image {
|
||||
@JsonIgnore
|
||||
public boolean isGrouped;
|
||||
@JsonIgnore
|
||||
public boolean isOneToOneConversation;
|
||||
@JsonIgnore
|
||||
public UserEntity activeUser;
|
||||
@JsonIgnore
|
||||
public Map<String, String> selectedIndividualHashMap;
|
||||
@JsonIgnore
|
||||
public boolean isLinkPreviewAllowed;
|
||||
List<MessageType> messageTypesToIgnore = Arrays.asList(MessageType.REGULAR_TEXT_MESSAGE,
|
||||
MessageType.SYSTEM_MESSAGE, MessageType.SINGLE_LINK_VIDEO_MESSAGE,
|
||||
MessageType.SINGLE_LINK_AUDIO_MESSAGE, MessageType.SINGLE_LINK_MESSAGE);
|
||||
@JsonField(name = "id")
|
||||
public int jsonMessageId;
|
||||
@JsonField(name = "token")
|
||||
public String token;
|
||||
// guests or users
|
||||
@JsonField(name = "actorType")
|
||||
public String actorType;
|
||||
@JsonField(name = "actorId")
|
||||
public String actorId;
|
||||
// send when crafting a message
|
||||
@JsonField(name = "actorDisplayName")
|
||||
public String actorDisplayName;
|
||||
@JsonField(name = "timestamp")
|
||||
public long timestamp;
|
||||
// send when crafting a message, max 1000 lines
|
||||
@JsonField(name = "message")
|
||||
public String message;
|
||||
@JsonField(name = "messageParameters")
|
||||
public HashMap<String, HashMap<String, String>> messageParameters;
|
||||
@JsonField(name = "systemMessage", typeConverter = EnumSystemMessageTypeConverter.class)
|
||||
public SystemMessageType systemMessageType;
|
||||
@JsonIgnore
|
||||
public boolean isGrouped;
|
||||
@JsonIgnore
|
||||
public boolean isOneToOneConversation;
|
||||
@JsonIgnore
|
||||
public UserEntity activeUser;
|
||||
@JsonIgnore
|
||||
public Map<String, String> selectedIndividualHashMap;
|
||||
@JsonIgnore
|
||||
public boolean isLinkPreviewAllowed;
|
||||
@JsonField(name = "id")
|
||||
public int jsonMessageId;
|
||||
@JsonField(name = "token")
|
||||
public String token;
|
||||
// guests or users
|
||||
@JsonField(name = "actorType")
|
||||
public String actorType;
|
||||
@JsonField(name = "actorId")
|
||||
public String actorId;
|
||||
// send when crafting a message
|
||||
@JsonField(name = "actorDisplayName")
|
||||
public String actorDisplayName;
|
||||
@JsonField(name = "timestamp")
|
||||
public long timestamp;
|
||||
// send when crafting a message, max 1000 lines
|
||||
@JsonField(name = "message")
|
||||
public String message;
|
||||
@JsonField(name = "messageParameters")
|
||||
public HashMap<String, HashMap<String, String>> messageParameters;
|
||||
@JsonField(name = "systemMessage", typeConverter = EnumSystemMessageTypeConverter.class)
|
||||
public SystemMessageType systemMessageType;
|
||||
List<MessageType> messageTypesToIgnore = Arrays.asList(MessageType.REGULAR_TEXT_MESSAGE,
|
||||
MessageType.SYSTEM_MESSAGE, MessageType.SINGLE_LINK_VIDEO_MESSAGE,
|
||||
MessageType.SINGLE_LINK_AUDIO_MESSAGE, MessageType.SINGLE_LINK_MESSAGE);
|
||||
|
||||
private boolean hasFileAttachment() {
|
||||
if (messageParameters != null && messageParameters.size() > 0) {
|
||||
for (String key : messageParameters.keySet()) {
|
||||
Map<String, String> individualHashMap = messageParameters.get(key);
|
||||
if (individualHashMap.get("type").equals("file")) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
private boolean hasFileAttachment() {
|
||||
if (messageParameters != null && messageParameters.size() > 0) {
|
||||
for (String key : messageParameters.keySet()) {
|
||||
Map<String, String> individualHashMap = messageParameters.get(key);
|
||||
if (individualHashMap.get("type").equals("file")) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public String getImageUrl() {
|
||||
if (messageParameters != null && messageParameters.size() > 0) {
|
||||
for (String key : messageParameters.keySet()) {
|
||||
Map<String, String> individualHashMap = messageParameters.get(key);
|
||||
if (individualHashMap.get("type").equals("file")) {
|
||||
selectedIndividualHashMap = individualHashMap;
|
||||
return (ApiUtils.getUrlForFilePreviewWithFileId(getActiveUser().getBaseUrl(),
|
||||
individualHashMap.get("id"), NextcloudTalkApplication.Companion.getSharedApplication().getResources().getDimensionPixelSize(R.dimen.maximum_file_preview_size)));
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public String getImageUrl() {
|
||||
if (messageParameters != null && messageParameters.size() > 0) {
|
||||
for (String key : messageParameters.keySet()) {
|
||||
Map<String, String> individualHashMap = messageParameters.get(key);
|
||||
if (individualHashMap.get("type").equals("file")) {
|
||||
selectedIndividualHashMap = individualHashMap;
|
||||
return (ApiUtils.getUrlForFilePreviewWithFileId(getActiveUser().getBaseUrl(),
|
||||
individualHashMap.get("id"), NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources()
|
||||
.getDimensionPixelSize(R.dimen.maximum_file_preview_size)));
|
||||
}
|
||||
|
||||
if (!messageTypesToIgnore.contains(getMessageType()) && isLinkPreviewAllowed) {
|
||||
return getMessage().trim();
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
public MessageType getMessageType() {
|
||||
if (!TextUtils.isEmpty(getSystemMessage())) {
|
||||
return MessageType.SYSTEM_MESSAGE;
|
||||
}
|
||||
|
||||
if (hasFileAttachment()) {
|
||||
return MessageType.SINGLE_NC_ATTACHMENT_MESSAGE;
|
||||
}
|
||||
|
||||
return TextMatchers.getMessageTypeFromString(getText());
|
||||
if (!messageTypesToIgnore.contains(getMessageType()) && isLinkPreviewAllowed) {
|
||||
return getMessage().trim();
|
||||
}
|
||||
|
||||
public Map<String, String> getSelectedIndividualHashMap() {
|
||||
return selectedIndividualHashMap;
|
||||
return null;
|
||||
}
|
||||
|
||||
public MessageType getMessageType() {
|
||||
if (!TextUtils.isEmpty(getSystemMessage())) {
|
||||
return MessageType.SYSTEM_MESSAGE;
|
||||
}
|
||||
|
||||
public void setSelectedIndividualHashMap(Map<String, String> selectedIndividualHashMap) {
|
||||
this.selectedIndividualHashMap = selectedIndividualHashMap;
|
||||
if (hasFileAttachment()) {
|
||||
return MessageType.SINGLE_NC_ATTACHMENT_MESSAGE;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getId() {
|
||||
return Integer.toString(jsonMessageId);
|
||||
}
|
||||
return TextMatchers.getMessageTypeFromString(getText());
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getText() {
|
||||
return ChatUtils.getParsedMessage(getMessage(), getMessageParameters());
|
||||
}
|
||||
public Map<String, String> getSelectedIndividualHashMap() {
|
||||
return selectedIndividualHashMap;
|
||||
}
|
||||
|
||||
public String getLastMessageDisplayText() {
|
||||
if (getMessageType().equals(MessageType.REGULAR_TEXT_MESSAGE) || getMessageType().equals(MessageType.SYSTEM_MESSAGE)) {
|
||||
return getText();
|
||||
public void setSelectedIndividualHashMap(Map<String, String> selectedIndividualHashMap) {
|
||||
this.selectedIndividualHashMap = selectedIndividualHashMap;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getId() {
|
||||
return Integer.toString(jsonMessageId);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getText() {
|
||||
return ChatUtils.getParsedMessage(getMessage(), getMessageParameters());
|
||||
}
|
||||
|
||||
public String getLastMessageDisplayText() {
|
||||
if (getMessageType().equals(MessageType.REGULAR_TEXT_MESSAGE) || getMessageType().equals(
|
||||
MessageType.SYSTEM_MESSAGE)) {
|
||||
return getText();
|
||||
} else {
|
||||
if (getMessageType().equals(MessageType.SINGLE_LINK_GIPHY_MESSAGE)
|
||||
|| getMessageType().equals(MessageType.SINGLE_LINK_TENOR_MESSAGE)
|
||||
|| getMessageType().equals(MessageType.SINGLE_LINK_GIF_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_sent_a_gif_you));
|
||||
} else {
|
||||
if (getMessageType().equals(MessageType.SINGLE_LINK_GIPHY_MESSAGE)
|
||||
|| getMessageType().equals(MessageType.SINGLE_LINK_TENOR_MESSAGE)
|
||||
|| getMessageType().equals(MessageType.SINGLE_LINK_GIF_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_sent_a_gif_you));
|
||||
} else {
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication().getResources().getString(R.string.nc_sent_a_gif),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName() : NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_guest)));
|
||||
}
|
||||
} else if (getMessageType().equals(MessageType.SINGLE_NC_ATTACHMENT_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_sent_an_attachment_you));
|
||||
} else {
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication().getResources().getString(R.string.nc_sent_an_attachment),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName() : NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_guest)));
|
||||
}
|
||||
} else if (getMessageType().equals(MessageType.SINGLE_LINK_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_sent_a_link_you));
|
||||
} else {
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication().getResources().getString(R.string.nc_sent_a_link),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName() : NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_guest)));
|
||||
}
|
||||
} else if (getMessageType().equals(MessageType.SINGLE_LINK_AUDIO_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_sent_an_audio_you));
|
||||
} else {
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication().getResources().getString(R.string.nc_sent_an_audio),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName() : NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_guest)));
|
||||
}
|
||||
} else if (getMessageType().equals(MessageType.SINGLE_LINK_VIDEO_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_sent_a_video_you));
|
||||
} else {
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication().getResources().getString(R.string.nc_sent_a_video),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName() : NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_guest)));
|
||||
}
|
||||
} else if (getMessageType().equals(MessageType.SINGLE_LINK_IMAGE_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_sent_an_image_you));
|
||||
} else {
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication().getResources().getString(R.string.nc_sent_an_image),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName() : NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_guest)));
|
||||
}
|
||||
}
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources()
|
||||
.getString(R.string.nc_sent_a_gif),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName()
|
||||
: NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_guest)));
|
||||
}
|
||||
|
||||
return "";
|
||||
} else if (getMessageType().equals(MessageType.SINGLE_NC_ATTACHMENT_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_sent_an_attachment_you));
|
||||
} else {
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources()
|
||||
.getString(R.string.nc_sent_an_attachment),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName()
|
||||
: NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_guest)));
|
||||
}
|
||||
} else if (getMessageType().equals(MessageType.SINGLE_LINK_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_sent_a_link_you));
|
||||
} else {
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources()
|
||||
.getString(R.string.nc_sent_a_link),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName()
|
||||
: NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_guest)));
|
||||
}
|
||||
} else if (getMessageType().equals(MessageType.SINGLE_LINK_AUDIO_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_sent_an_audio_you));
|
||||
} else {
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources()
|
||||
.getString(R.string.nc_sent_an_audio),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName()
|
||||
: NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_guest)));
|
||||
}
|
||||
} else if (getMessageType().equals(MessageType.SINGLE_LINK_VIDEO_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_sent_a_video_you));
|
||||
} else {
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources()
|
||||
.getString(R.string.nc_sent_a_video),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName()
|
||||
: NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_guest)));
|
||||
}
|
||||
} else if (getMessageType().equals(MessageType.SINGLE_LINK_IMAGE_MESSAGE)) {
|
||||
if (getActorId().equals(getActiveUser().getUserId())) {
|
||||
return (NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_sent_an_image_you));
|
||||
} else {
|
||||
return (String.format(NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getResources()
|
||||
.getString(R.string.nc_sent_an_image),
|
||||
!TextUtils.isEmpty(getActorDisplayName()) ? getActorDisplayName()
|
||||
: NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_guest)));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public IUser getUser() {
|
||||
return new IUser() {
|
||||
@Override
|
||||
public String getId() {
|
||||
return actorId;
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return actorDisplayName;
|
||||
}
|
||||
@Override
|
||||
public IUser getUser() {
|
||||
return new IUser() {
|
||||
@Override
|
||||
public String getId() {
|
||||
return actorId;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getAvatar() {
|
||||
if (getActorType().equals("users")) {
|
||||
return ApiUtils.getUrlForAvatarWithName(getActiveUser().getBaseUrl(), actorId, R.dimen.avatar_size);
|
||||
} else if (getActorType().equals("guests")) {
|
||||
String apiId =
|
||||
NextcloudTalkApplication.Companion.getSharedApplication().getString(R.string.nc_guest);
|
||||
@Override
|
||||
public String getName() {
|
||||
return actorDisplayName;
|
||||
}
|
||||
|
||||
if (!TextUtils.isEmpty(getActorDisplayName())) {
|
||||
apiId = getActorDisplayName();
|
||||
}
|
||||
return ApiUtils.getUrlForAvatarWithNameForGuests(getActiveUser().getBaseUrl(), apiId, R.dimen.avatar_size);
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
@Override
|
||||
public String getAvatar() {
|
||||
if (getActorType().equals("users")) {
|
||||
return ApiUtils.getUrlForAvatarWithName(getActiveUser().getBaseUrl(), actorId,
|
||||
R.dimen.avatar_size);
|
||||
} else if (getActorType().equals("guests")) {
|
||||
String apiId =
|
||||
NextcloudTalkApplication.Companion.getSharedApplication()
|
||||
.getString(R.string.nc_guest);
|
||||
|
||||
@Override
|
||||
public Date getCreatedAt() {
|
||||
return new Date(timestamp * 1000L);
|
||||
}
|
||||
if (!TextUtils.isEmpty(getActorDisplayName())) {
|
||||
apiId = getActorDisplayName();
|
||||
}
|
||||
return ApiUtils.getUrlForAvatarWithNameForGuests(getActiveUser().getBaseUrl(), apiId,
|
||||
R.dimen.avatar_size);
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getSystemMessage() {
|
||||
return new EnumSystemMessageTypeConverter().convertToString(getSystemMessageType());
|
||||
}
|
||||
@Override
|
||||
public Date getCreatedAt() {
|
||||
return new Date(timestamp * 1000L);
|
||||
}
|
||||
|
||||
public enum MessageType {
|
||||
REGULAR_TEXT_MESSAGE,
|
||||
SYSTEM_MESSAGE,
|
||||
SINGLE_LINK_GIPHY_MESSAGE,
|
||||
SINGLE_LINK_TENOR_MESSAGE,
|
||||
SINGLE_LINK_GIF_MESSAGE,
|
||||
SINGLE_LINK_MESSAGE,
|
||||
SINGLE_LINK_VIDEO_MESSAGE,
|
||||
SINGLE_LINK_IMAGE_MESSAGE,
|
||||
SINGLE_LINK_AUDIO_MESSAGE,
|
||||
SINGLE_NC_ATTACHMENT_MESSAGE,
|
||||
}
|
||||
@Override
|
||||
public String getSystemMessage() {
|
||||
return new EnumSystemMessageTypeConverter().convertToString(getSystemMessageType());
|
||||
}
|
||||
|
||||
public enum SystemMessageType {
|
||||
DUMMY,
|
||||
CONVERSATION_CREATED,
|
||||
CONVERSATION_RENAMED,
|
||||
CALL_STARTED,
|
||||
CALL_JOINED,
|
||||
CALL_LEFT,
|
||||
CALL_ENDED,
|
||||
GUESTS_ALLOWED,
|
||||
GUESTS_DISALLOWED,
|
||||
PASSWORD_SET,
|
||||
PASSWORD_REMOVED,
|
||||
USER_ADDED,
|
||||
USER_REMOVED,
|
||||
MODERATOR_PROMOTED,
|
||||
MODERATOR_DEMOTED,
|
||||
FILE_SHARED,
|
||||
LOBBY_NONE,
|
||||
LOBBY_NON_MODERATORS,
|
||||
LOBBY_OPEN_TO_EVERYONE
|
||||
}
|
||||
public enum MessageType {
|
||||
REGULAR_TEXT_MESSAGE,
|
||||
SYSTEM_MESSAGE,
|
||||
SINGLE_LINK_GIPHY_MESSAGE,
|
||||
SINGLE_LINK_TENOR_MESSAGE,
|
||||
SINGLE_LINK_GIF_MESSAGE,
|
||||
SINGLE_LINK_MESSAGE,
|
||||
SINGLE_LINK_VIDEO_MESSAGE,
|
||||
SINGLE_LINK_IMAGE_MESSAGE,
|
||||
SINGLE_LINK_AUDIO_MESSAGE,
|
||||
SINGLE_NC_ATTACHMENT_MESSAGE,
|
||||
}
|
||||
|
||||
public enum SystemMessageType {
|
||||
DUMMY,
|
||||
CONVERSATION_CREATED,
|
||||
CONVERSATION_RENAMED,
|
||||
CALL_STARTED,
|
||||
CALL_JOINED,
|
||||
CALL_LEFT,
|
||||
CALL_ENDED,
|
||||
GUESTS_ALLOWED,
|
||||
GUESTS_DISALLOWED,
|
||||
PASSWORD_SET,
|
||||
PASSWORD_REMOVED,
|
||||
USER_ADDED,
|
||||
USER_REMOVED,
|
||||
MODERATOR_PROMOTED,
|
||||
MODERATOR_DEMOTED,
|
||||
FILE_SHARED,
|
||||
LOBBY_NONE,
|
||||
LOBBY_NON_MODERATORS,
|
||||
LOBBY_OPEN_TO_EVERYONE
|
||||
}
|
||||
}
|
||||
|
@ -30,6 +30,6 @@ import org.parceler.Parcel;
|
||||
@Parcel
|
||||
@JsonObject
|
||||
public class ChatOCS extends GenericOCS {
|
||||
@JsonField(name = "data")
|
||||
public List<ChatMessage> data;
|
||||
@JsonField(name = "data")
|
||||
public List<ChatMessage> data;
|
||||
}
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user