Media : branch upload to preview screen (need improvement)
This commit is contained in:
@@ -14,11 +14,12 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package io.element.android.libraries.mediaupload.api
|
||||
package io.element.android.features.messages.impl.attachments.preview
|
||||
|
||||
sealed interface MediaType {
|
||||
object Image : MediaType
|
||||
object Video : MediaType
|
||||
object Audio : MediaType
|
||||
object File : MediaType
|
||||
import androidx.compose.runtime.Immutable
|
||||
|
||||
@Immutable
|
||||
sealed interface AttachmentsPreviewEvents {
|
||||
object SendAttachment : AttachmentsPreviewEvents
|
||||
object ClearSendState : AttachmentsPreviewEvents
|
||||
}
|
||||
@@ -16,15 +16,32 @@
|
||||
|
||||
package io.element.android.features.messages.impl.attachments.preview
|
||||
|
||||
import android.net.Uri
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.MutableState
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
import androidx.compose.runtime.remember
|
||||
import androidx.compose.runtime.rememberCoroutineScope
|
||||
import dagger.assisted.Assisted
|
||||
import dagger.assisted.AssistedFactory
|
||||
import dagger.assisted.AssistedInject
|
||||
import io.element.android.features.messages.impl.attachments.Attachment
|
||||
import io.element.android.libraries.architecture.Async
|
||||
import io.element.android.libraries.architecture.Presenter
|
||||
import io.element.android.libraries.architecture.executeResult
|
||||
import io.element.android.libraries.core.extensions.flatMap
|
||||
import io.element.android.libraries.designsystem.utils.SnackbarDispatcher
|
||||
import io.element.android.libraries.matrix.api.room.MatrixRoom
|
||||
import io.element.android.libraries.mediaupload.api.MediaPreProcessor
|
||||
import io.element.android.libraries.mediaupload.api.sendMedia
|
||||
import kotlinx.coroutines.CoroutineScope
|
||||
import kotlinx.coroutines.launch
|
||||
|
||||
class AttachmentsPreviewPresenter @AssistedInject constructor(
|
||||
@Assisted private val attachment: Attachment,
|
||||
private val room: MatrixRoom,
|
||||
private val mediaPreProcessor: MediaPreProcessor,
|
||||
private val snackbarDispatcher: SnackbarDispatcher,
|
||||
) : Presenter<AttachmentsPreviewState> {
|
||||
|
||||
@AssistedFactory
|
||||
@@ -35,8 +52,54 @@ class AttachmentsPreviewPresenter @AssistedInject constructor(
|
||||
@Composable
|
||||
override fun present(): AttachmentsPreviewState {
|
||||
|
||||
val coroutineScope = rememberCoroutineScope()
|
||||
|
||||
val sendActionState = remember {
|
||||
mutableStateOf<Async<Unit>>(Async.Uninitialized)
|
||||
}
|
||||
|
||||
fun handleEvents(attachmentsPreviewEvents: AttachmentsPreviewEvents) {
|
||||
when (attachmentsPreviewEvents) {
|
||||
AttachmentsPreviewEvents.SendAttachment -> coroutineScope.sendAttachment(attachment, sendActionState)
|
||||
AttachmentsPreviewEvents.ClearSendState -> sendActionState.value = Async.Uninitialized
|
||||
}
|
||||
}
|
||||
|
||||
return AttachmentsPreviewState(
|
||||
attachment = attachment,
|
||||
sendActionState = sendActionState.value,
|
||||
eventSink = ::handleEvents
|
||||
)
|
||||
}
|
||||
|
||||
private fun CoroutineScope.sendAttachment(
|
||||
attachment: Attachment,
|
||||
sendActionState: MutableState<Async<Unit>>,
|
||||
) = launch {
|
||||
when (attachment) {
|
||||
is Attachment.Media -> {
|
||||
sendMedia(
|
||||
uri = attachment.localMedia.uri,
|
||||
mimeType = attachment.localMedia.mimeType,
|
||||
deleteOriginal = false,
|
||||
sendActionState = sendActionState
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private suspend fun sendMedia(
|
||||
uri: Uri,
|
||||
mimeType: String,
|
||||
deleteOriginal: Boolean = false,
|
||||
sendActionState: MutableState<Async<Unit>>,
|
||||
) {
|
||||
suspend {
|
||||
mediaPreProcessor
|
||||
.process(uri, mimeType, deleteOriginal)
|
||||
.flatMap { info ->
|
||||
room.sendMedia(info)
|
||||
}
|
||||
}.executeResult(sendActionState)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -17,7 +17,10 @@
|
||||
package io.element.android.features.messages.impl.attachments.preview
|
||||
|
||||
import io.element.android.features.messages.impl.attachments.Attachment
|
||||
import io.element.android.libraries.architecture.Async
|
||||
|
||||
data class AttachmentsPreviewState(
|
||||
val attachment: Attachment,
|
||||
val sendActionState: Async<Unit>,
|
||||
val eventSink: (AttachmentsPreviewEvents) -> Unit
|
||||
)
|
||||
|
||||
@@ -20,17 +20,23 @@ import androidx.compose.ui.tooling.preview.PreviewParameterProvider
|
||||
import androidx.core.net.toUri
|
||||
import io.element.android.features.messages.impl.attachments.Attachment
|
||||
import io.element.android.features.messages.impl.media.local.LocalMedia
|
||||
import io.element.android.libraries.architecture.Async
|
||||
import io.element.android.libraries.core.mimetype.MimeTypes
|
||||
|
||||
open class AttachmentsPreviewStateProvider : PreviewParameterProvider<AttachmentsPreviewState> {
|
||||
override val values: Sequence<AttachmentsPreviewState>
|
||||
get() = sequenceOf(
|
||||
aAttachmentsPreviewState(),
|
||||
anAttachmentsPreviewState(),
|
||||
anAttachmentsPreviewState(sendActionState = Async.Loading()),
|
||||
anAttachmentsPreviewState(sendActionState = Async.Failure(RuntimeException())),
|
||||
// Add other states here
|
||||
)
|
||||
}
|
||||
|
||||
fun aAttachmentsPreviewState() = AttachmentsPreviewState(
|
||||
fun anAttachmentsPreviewState(sendActionState: Async<Unit> = Async.Uninitialized) = AttachmentsPreviewState(
|
||||
attachment = Attachment.Media(
|
||||
localMedia = LocalMedia("".toUri(), mimeType = null)
|
||||
)
|
||||
localMedia = LocalMedia("".toUri(), mimeType = MimeTypes.OctetStream),
|
||||
),
|
||||
sendActionState = sendActionState,
|
||||
eventSink = {}
|
||||
)
|
||||
|
||||
@@ -29,17 +29,23 @@ import androidx.compose.foundation.layout.height
|
||||
import androidx.compose.foundation.layout.padding
|
||||
import androidx.compose.material3.ExperimentalMaterial3Api
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.LaunchedEffect
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.tooling.preview.Preview
|
||||
import androidx.compose.ui.tooling.preview.PreviewParameter
|
||||
import androidx.compose.ui.unit.dp
|
||||
import io.element.android.features.messages.impl.attachments.Attachment
|
||||
import io.element.android.features.messages.impl.attachments.preview.error.sendAttachmentError
|
||||
import io.element.android.features.messages.impl.media.local.LocalMediaView
|
||||
import io.element.android.libraries.architecture.Async
|
||||
import io.element.android.libraries.designsystem.components.ProgressDialog
|
||||
import io.element.android.libraries.designsystem.components.dialogs.RetryDialog
|
||||
import io.element.android.libraries.designsystem.preview.ElementPreviewDark
|
||||
import io.element.android.libraries.designsystem.theme.components.Scaffold
|
||||
import io.element.android.libraries.designsystem.theme.components.Text
|
||||
import io.element.android.libraries.designsystem.theme.components.TextButton
|
||||
import io.element.android.libraries.ui.strings.R
|
||||
import io.element.android.libraries.ui.strings.R as StringsR
|
||||
|
||||
@Composable
|
||||
@@ -49,39 +55,93 @@ fun AttachmentsPreviewView(
|
||||
modifier: Modifier = Modifier,
|
||||
) {
|
||||
|
||||
fun onSendClicked() {
|
||||
fun postSendAttachment() {
|
||||
state.eventSink(AttachmentsPreviewEvents.SendAttachment)
|
||||
}
|
||||
|
||||
fun postClearSendState() {
|
||||
state.eventSink(AttachmentsPreviewEvents.ClearSendState)
|
||||
}
|
||||
|
||||
if (state.sendActionState is Async.Success) {
|
||||
LaunchedEffect(state.sendActionState) {
|
||||
onDismiss()
|
||||
}
|
||||
}
|
||||
|
||||
Scaffold(modifier) {
|
||||
Column(
|
||||
modifier = Modifier.fillMaxWidth(),
|
||||
) {
|
||||
Spacer(
|
||||
modifier = Modifier.height(80.dp)
|
||||
Box {
|
||||
AttachmentPreviewContent(
|
||||
attachment = state.attachment,
|
||||
onSendClicked = ::postSendAttachment,
|
||||
onDismiss = onDismiss
|
||||
)
|
||||
Box(
|
||||
modifier = Modifier
|
||||
.fillMaxWidth()
|
||||
.weight(1f)
|
||||
) {
|
||||
when (state.attachment) {
|
||||
is Attachment.Media -> LocalMediaView(
|
||||
localMedia = state.attachment.localMedia
|
||||
)
|
||||
}
|
||||
}
|
||||
AttachmentsPreviewBottomActions(
|
||||
onCancelClicked = onDismiss,
|
||||
onSendClicked = ::onSendClicked,
|
||||
modifier = Modifier
|
||||
.fillMaxWidth()
|
||||
.defaultMinSize(minHeight = 120.dp)
|
||||
.padding(all = 24.dp)
|
||||
AttachmentSendStateView(
|
||||
sendActionState = state.sendActionState,
|
||||
onRetryClicked = ::postSendAttachment,
|
||||
onRetryDismissed = ::postClearSendState
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun AttachmentSendStateView(
|
||||
sendActionState: Async<Unit>,
|
||||
onRetryDismissed: () -> Unit,
|
||||
onRetryClicked: () -> Unit
|
||||
) {
|
||||
when (sendActionState) {
|
||||
is Async.Loading -> {
|
||||
ProgressDialog(text = stringResource(id = R.string.common_loading))
|
||||
}
|
||||
|
||||
is Async.Failure -> {
|
||||
RetryDialog(
|
||||
content = stringResource(sendAttachmentError(sendActionState.error)),
|
||||
onDismiss = onRetryDismissed,
|
||||
onRetry = onRetryClicked
|
||||
)
|
||||
}
|
||||
|
||||
else -> Unit
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun AttachmentPreviewContent(
|
||||
attachment: Attachment,
|
||||
onSendClicked: () -> Unit,
|
||||
onDismiss: () -> Unit
|
||||
) {
|
||||
Column(
|
||||
modifier = Modifier.fillMaxWidth(),
|
||||
) {
|
||||
Spacer(
|
||||
modifier = Modifier.height(80.dp)
|
||||
)
|
||||
Box(
|
||||
modifier = Modifier
|
||||
.fillMaxWidth()
|
||||
.weight(1f)
|
||||
) {
|
||||
when (attachment) {
|
||||
is Attachment.Media -> LocalMediaView(
|
||||
localMedia = attachment.localMedia
|
||||
)
|
||||
}
|
||||
}
|
||||
AttachmentsPreviewBottomActions(
|
||||
onCancelClicked = onDismiss,
|
||||
onSendClicked = onSendClicked,
|
||||
modifier = Modifier
|
||||
.fillMaxWidth()
|
||||
.defaultMinSize(minHeight = 120.dp)
|
||||
.padding(all = 24.dp)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun AttachmentsPreviewBottomActions(
|
||||
onCancelClicked: () -> Unit,
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
/*
|
||||
* Copyright (c) 2022 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package io.element.android.features.messages.impl.attachments.preview.error
|
||||
|
||||
import io.element.android.libraries.mediaupload.api.MediaPreProcessor
|
||||
import io.element.android.libraries.ui.strings.R
|
||||
|
||||
fun sendAttachmentError(
|
||||
throwable: Throwable
|
||||
): Int {
|
||||
return if (throwable is MediaPreProcessor.Failure) {
|
||||
R.string.screen_media_upload_preview_error_failed_processing
|
||||
} else {
|
||||
R.string.screen_media_upload_preview_error_failed_sending
|
||||
}
|
||||
}
|
||||
@@ -19,6 +19,7 @@ package io.element.android.features.messages.impl.media.local
|
||||
import android.content.Context
|
||||
import android.net.Uri
|
||||
import com.squareup.anvil.annotations.ContributesBinding
|
||||
import io.element.android.libraries.core.mimetype.MimeTypes
|
||||
import io.element.android.libraries.di.AppScope
|
||||
import io.element.android.libraries.di.ApplicationContext
|
||||
import javax.inject.Inject
|
||||
@@ -30,7 +31,7 @@ class AndroidLocalMediaFactory @Inject constructor(
|
||||
|
||||
override fun createFromUri(uri: Uri?, mimeType: String?): LocalMedia? {
|
||||
if (uri == null) return null
|
||||
val resolvedMimeType = mimeType ?: context.contentResolver.getType(uri)
|
||||
val resolvedMimeType = mimeType ?: context.contentResolver.getType(uri) ?: MimeTypes.OctetStream
|
||||
return LocalMedia(uri, resolvedMimeType)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -17,13 +17,14 @@
|
||||
package io.element.android.features.messages.impl.media.local
|
||||
|
||||
import android.net.Uri
|
||||
import io.element.android.libraries.core.mimetype.MimeTypes
|
||||
|
||||
class FakeLocalMediaFactory() : LocalMediaFactory {
|
||||
|
||||
var mimeType: String? = null
|
||||
var fallbackMimeType: String = MimeTypes.OctetStream
|
||||
|
||||
override fun createFromUri(uri: Uri?, mimeType: String?): LocalMedia? {
|
||||
if (uri == null) return null
|
||||
return LocalMedia(uri, mimeType)
|
||||
return LocalMedia(uri, mimeType ?: fallbackMimeType)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -23,5 +23,5 @@ import kotlinx.parcelize.Parcelize
|
||||
@Parcelize
|
||||
data class LocalMedia(
|
||||
val uri: Uri,
|
||||
val mimeType: String?,
|
||||
val mimeType: String,
|
||||
) : Parcelable
|
||||
|
||||
@@ -19,5 +19,10 @@ package io.element.android.features.messages.impl.media.local
|
||||
import android.net.Uri
|
||||
|
||||
interface LocalMediaFactory {
|
||||
/**
|
||||
* This method will create a [LocalMedia] with the given [uri] and [mimeType]
|
||||
* If the [mimeType] is null, it'll try to read it from the content.
|
||||
*
|
||||
*/
|
||||
fun createFromUri(uri: Uri?, mimeType: String?): LocalMedia?
|
||||
}
|
||||
|
||||
@@ -34,7 +34,6 @@ import io.element.android.libraries.core.data.StableCharSequence
|
||||
import io.element.android.libraries.core.data.toStableCharSequence
|
||||
import io.element.android.libraries.core.mimetype.MimeTypes
|
||||
import io.element.android.libraries.designsystem.utils.SnackbarDispatcher
|
||||
import io.element.android.libraries.designsystem.utils.SnackbarMessage
|
||||
import io.element.android.libraries.di.RoomScope
|
||||
import io.element.android.libraries.di.SingleIn
|
||||
import io.element.android.libraries.featureflag.api.FeatureFlagService
|
||||
@@ -42,15 +41,11 @@ import io.element.android.libraries.featureflag.api.FeatureFlags
|
||||
import io.element.android.libraries.matrix.api.room.MatrixRoom
|
||||
import io.element.android.libraries.mediapickers.api.PickerProvider
|
||||
import io.element.android.libraries.mediaupload.api.MediaPreProcessor
|
||||
import io.element.android.libraries.mediaupload.api.MediaType
|
||||
import io.element.android.libraries.mediaupload.api.sendMedia
|
||||
import io.element.android.libraries.textcomposer.MessageComposerMode
|
||||
import kotlinx.collections.immutable.persistentListOf
|
||||
import kotlinx.coroutines.CoroutineScope
|
||||
import kotlinx.coroutines.launch
|
||||
import timber.log.Timber
|
||||
import javax.inject.Inject
|
||||
import io.element.android.libraries.ui.strings.R as StringR
|
||||
|
||||
@SingleIn(RoomScope::class)
|
||||
class MessageComposerPresenter @Inject constructor(
|
||||
@@ -59,8 +54,6 @@ class MessageComposerPresenter @Inject constructor(
|
||||
private val mediaPickerProvider: PickerProvider,
|
||||
private val featureFlagService: FeatureFlagService,
|
||||
private val localMediaFactory: LocalMediaFactory,
|
||||
private val mediaPreProcessor: MediaPreProcessor,
|
||||
private val snackbarDispatcher: SnackbarDispatcher,
|
||||
) : Presenter<MessageComposerState> {
|
||||
|
||||
@SuppressLint("UnsafeOptInUsageError")
|
||||
@@ -186,26 +179,4 @@ class MessageComposerPresenter @Inject constructor(
|
||||
}
|
||||
}
|
||||
|
||||
private fun CoroutineScope.sendMedia(
|
||||
uri: Uri,
|
||||
mediaType: MediaType,
|
||||
deleteOriginal: Boolean = false
|
||||
) = launch {
|
||||
mediaPreProcessor.process(uri, mediaType, deleteOriginal)
|
||||
.map { info ->
|
||||
room.sendMedia(info)
|
||||
}
|
||||
.onSuccess {
|
||||
Timber.d("onSuccess sending media")
|
||||
}.onFailure { failure ->
|
||||
Timber.e(failure, "onfailure sending media: $failure")
|
||||
val snackbarMessage = if (failure is MediaPreProcessor.Failure) {
|
||||
StringR.string.screen_media_upload_preview_error_failed_processing
|
||||
} else {
|
||||
StringR.string.screen_media_upload_preview_error_failed_sending
|
||||
}
|
||||
snackbarDispatcher.post(SnackbarMessage(snackbarMessage))
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -25,3 +25,16 @@ inline fun <R, T : R> Result<T>.mapFailure(transform: (exception: Throwable) ->
|
||||
else -> Result.failure(transform(exception))
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Can be used to transform some Throwable into some other.
|
||||
*/
|
||||
inline fun <R, T> Result<R>.flatMap(transform: (R) -> Result<T>): Result<T> {
|
||||
return when (val exception = exceptionOrNull()) {
|
||||
null -> mapCatching(transform).fold(
|
||||
onSuccess = { it },
|
||||
onFailure = { Result.failure(it) }
|
||||
)
|
||||
else -> Result.failure(exception)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -20,13 +20,13 @@ import android.net.Uri
|
||||
|
||||
interface MediaPreProcessor {
|
||||
/**
|
||||
* Given a [uri] and [mediaType], pre-processes the media before it's uploaded, resizing, transcoding, and removing sensitive info from its metadata.
|
||||
* Given a [uri] and [mimeType], pre-processes the media before it's uploaded, resizing, transcoding, and removing sensitive info from its metadata.
|
||||
* If [deleteOriginal] is `true`, the file reference by the [uri] will be automatically deleted too when this process finishes.
|
||||
* @return a [Result] with the [MediaUploadInfo] containing all the info needed to begin the upload.
|
||||
*/
|
||||
suspend fun process(
|
||||
uri: Uri,
|
||||
mediaType: MediaType,
|
||||
mimeType: String,
|
||||
deleteOriginal: Boolean = false
|
||||
): Result<MediaUploadInfo>
|
||||
|
||||
|
||||
@@ -27,7 +27,9 @@ import io.element.android.libraries.androidutils.media.runAndRelease
|
||||
import io.element.android.libraries.core.data.tryOrNull
|
||||
import io.element.android.libraries.core.extensions.mapFailure
|
||||
import io.element.android.libraries.core.mimetype.MimeTypes
|
||||
import io.element.android.libraries.core.mimetype.MimeTypes.isMimeTypeAudio
|
||||
import io.element.android.libraries.core.mimetype.MimeTypes.isMimeTypeImage
|
||||
import io.element.android.libraries.core.mimetype.MimeTypes.isMimeTypeVideo
|
||||
import io.element.android.libraries.di.AppScope
|
||||
import io.element.android.libraries.di.ApplicationContext
|
||||
import io.element.android.libraries.matrix.api.media.AudioInfo
|
||||
@@ -37,7 +39,6 @@ import io.element.android.libraries.matrix.api.media.MediaSource
|
||||
import io.element.android.libraries.matrix.api.media.ThumbnailInfo
|
||||
import io.element.android.libraries.matrix.api.media.VideoInfo
|
||||
import io.element.android.libraries.mediaupload.api.MediaPreProcessor
|
||||
import io.element.android.libraries.mediaupload.api.MediaType
|
||||
import io.element.android.libraries.mediaupload.api.MediaUploadInfo
|
||||
import io.element.android.libraries.mediaupload.api.ThumbnailProcessingInfo
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
@@ -53,7 +54,7 @@ import javax.inject.Inject
|
||||
import kotlin.time.Duration.Companion.seconds
|
||||
|
||||
@ContributesBinding(AppScope::class)
|
||||
class MediaPreProcessorImpl @Inject constructor(
|
||||
class AndroidMediaPreProcessor @Inject constructor(
|
||||
@ApplicationContext private val context: Context,
|
||||
private val imageCompressor: ImageCompressor,
|
||||
private val videoCompressor: VideoCompressor,
|
||||
@@ -89,27 +90,18 @@ class MediaPreProcessorImpl @Inject constructor(
|
||||
|
||||
override suspend fun process(
|
||||
uri: Uri,
|
||||
mediaType: MediaType,
|
||||
mimeType: String,
|
||||
deleteOriginal: Boolean,
|
||||
): Result<MediaUploadInfo> = runCatching {
|
||||
// Camera returns an 'octet-stream' mimetype, so it needs to be overridden
|
||||
val mimeType = contentResolver.getType(uri)
|
||||
val mimeTypeOrDefault = if (mimeType == MimeTypes.OctetStream) {
|
||||
when (mediaType) {
|
||||
MediaType.Image -> MimeTypes.Jpeg
|
||||
MediaType.Video -> MimeTypes.Mp4
|
||||
MediaType.Audio -> MimeTypes.Ogg
|
||||
else -> mimeType
|
||||
}
|
||||
} else {
|
||||
mimeType
|
||||
}
|
||||
val compressBeforeSending = mediaType in sequenceOf(MediaType.Image, MediaType.Video)
|
||||
val result = if (compressBeforeSending && mimeType != MimeTypes.Gif) {
|
||||
when (mediaType) {
|
||||
MediaType.Image -> processImage(uri)
|
||||
MediaType.Video -> processVideo(uri, mimeTypeOrDefault)
|
||||
MediaType.Audio -> processAudio(uri, mimeTypeOrDefault)
|
||||
val compressBeforeSending = (
|
||||
mimeType.isMimeTypeImage() && mimeType != MimeTypes.Gif) ||
|
||||
mimeType.isMimeTypeVideo()
|
||||
|
||||
val result = if (compressBeforeSending) {
|
||||
when {
|
||||
mimeType.isMimeTypeImage() -> processImage(uri)
|
||||
mimeType.isMimeTypeVideo() -> processVideo(uri, mimeType)
|
||||
mimeType.isMimeTypeAudio() -> processAudio(uri, mimeType)
|
||||
else -> error("Cannot compress file of type: $mimeType")
|
||||
}
|
||||
} else {
|
||||
@@ -19,7 +19,6 @@ package io.element.android.libraries.mediaupload.test
|
||||
import android.net.Uri
|
||||
import io.element.android.libraries.matrix.api.media.FileInfo
|
||||
import io.element.android.libraries.mediaupload.api.MediaPreProcessor
|
||||
import io.element.android.libraries.mediaupload.api.MediaType
|
||||
import io.element.android.libraries.mediaupload.api.MediaUploadInfo
|
||||
import java.io.File
|
||||
|
||||
@@ -37,7 +36,7 @@ class FakeMediaPreProcessor : MediaPreProcessor {
|
||||
)
|
||||
)
|
||||
|
||||
override suspend fun process(uri: Uri, mediaType: MediaType, deleteOriginal: Boolean): Result<MediaUploadInfo> = result
|
||||
override suspend fun process(uri: Uri, mimeType: String, deleteOriginal: Boolean): Result<MediaUploadInfo> = result
|
||||
|
||||
fun givenResult(value: Result<MediaUploadInfo>) {
|
||||
this.result = value
|
||||
|
||||
Reference in New Issue
Block a user