diff --git a/VisualNovel/app/src/main/java/com/remax/visualnovel/api/service/ChatService.kt b/VisualNovel/app/src/main/java/com/remax/visualnovel/api/service/ChatService.kt index 11e01f5..b8c0d30 100644 --- a/VisualNovel/app/src/main/java/com/remax/visualnovel/api/service/ChatService.kt +++ b/VisualNovel/app/src/main/java/com/remax/visualnovel/api/service/ChatService.kt @@ -7,7 +7,6 @@ import com.remax.visualnovel.entity.request.AIIsShowDTO import com.remax.visualnovel.entity.request.ChatAlbum import com.remax.visualnovel.entity.request.ChatSetting import com.remax.visualnovel.entity.request.HeartbeatBuy -import com.remax.visualnovel.entity.request.ParamBgUpload import com.remax.visualnovel.entity.request.ParamLanguage import com.remax.visualnovel.entity.request.ParamSoundList import com.remax.visualnovel.entity.request.ParamUserid @@ -19,12 +18,12 @@ import com.remax.visualnovel.entity.response.Album import com.remax.visualnovel.entity.response.Character import com.remax.visualnovel.entity.response.ChatAiModule import com.remax.visualnovel.entity.response.ChatBackgroundBase -import com.remax.visualnovel.entity.response.ChatModel import com.remax.visualnovel.entity.response.ChatSet import com.remax.visualnovel.entity.response.ChatSound import com.remax.visualnovel.entity.response.Friends import com.remax.visualnovel.entity.response.HeartbeatLevelOutput import com.remax.visualnovel.entity.response.Pageable +import com.remax.visualnovel.entity.response.RespBgUpload import com.remax.visualnovel.entity.response.Token import com.remax.visualnovel.entity.response.VoiceASR import com.remax.visualnovel.entity.response.base.Response @@ -32,11 +31,11 @@ import com.remax.visualnovel.entity.response.basenew.ResponseNew import okhttp3.MultipartBody import okhttp3.RequestBody import retrofit2.http.Body -import retrofit2.http.Field -import retrofit2.http.FormUrlEncoded import retrofit2.http.Multipart import retrofit2.http.POST import retrofit2.http.Part +import retrofit2.http.PartMap + interface ChatService { @@ -180,22 +179,17 @@ interface ChatService { @POST(BuildConfig.API_BASE + "/model/config/list") suspend fun requestAiModelList(@Body language: ParamLanguage): ResponseNew> - - - @POST(BuildConfig.API_BASE + "/file/bgImage/upload") - suspend fun uploadCustomBgPic(@Body param: ParamBgUpload): ResponseNew - - /*@Multipart - @POST(BuildConfig.API_BASE + "/file/bgImage/upload") - suspend fun uploadCustomBgPic(@Part("userId") title: RequestBody, - @Part file: MultipartBody.Part): ResponseNew*/ - - @POST(BuildConfig.API_BASE + "/file/bgImage/list") suspend fun requestChatBgList(@Body userId: ParamUserid): ResponseNew> - /*@FormUrlEncoded - @POST(BuildConfig.API_BASE + "/file/bgImage/list") - suspend fun requestChatBgList(@Field("userId") userId: Int): ResponseNew>*/ + + + @Multipart + @POST(BuildConfig.API_BASE + "/file/bgImage/upload") + fun uploadCustomBgPic( + @PartMap params: Map, + @Part file: MultipartBody.Part + ): ResponseNew + diff --git a/VisualNovel/app/src/main/java/com/remax/visualnovel/entity/request/ParamBgUpload.kt b/VisualNovel/app/src/main/java/com/remax/visualnovel/entity/request/ParamBgUpload.kt index 8a3390c..a15ac15 100644 --- a/VisualNovel/app/src/main/java/com/remax/visualnovel/entity/request/ParamBgUpload.kt +++ b/VisualNovel/app/src/main/java/com/remax/visualnovel/entity/request/ParamBgUpload.kt @@ -3,5 +3,4 @@ package com.remax.visualnovel.entity.request data class ParamBgUpload( var userId: String, - var file: String, ) diff --git a/VisualNovel/app/src/main/java/com/remax/visualnovel/entity/response/RespBgUpload.kt b/VisualNovel/app/src/main/java/com/remax/visualnovel/entity/response/RespBgUpload.kt new file mode 100644 index 0000000..5971da4 --- /dev/null +++ b/VisualNovel/app/src/main/java/com/remax/visualnovel/entity/response/RespBgUpload.kt @@ -0,0 +1,5 @@ +package com.remax.visualnovel.entity.response + +data class RespBgUpload ( + val url: String, +) \ No newline at end of file diff --git a/VisualNovel/app/src/main/java/com/remax/visualnovel/repository/api/ChatRepository.kt b/VisualNovel/app/src/main/java/com/remax/visualnovel/repository/api/ChatRepository.kt index e5433d8..78ba317 100644 --- a/VisualNovel/app/src/main/java/com/remax/visualnovel/repository/api/ChatRepository.kt +++ b/VisualNovel/app/src/main/java/com/remax/visualnovel/repository/api/ChatRepository.kt @@ -1,5 +1,7 @@ package com.remax.visualnovel.repository.api +import android.net.Uri +import androidx.core.net.toFile import com.remax.visualnovel.api.service.ChatService import com.remax.visualnovel.entity.request.ChatSetting import com.remax.visualnovel.entity.request.ParamBgUpload @@ -9,6 +11,10 @@ import com.remax.visualnovel.entity.request.ParamUserid import com.remax.visualnovel.entity.request.SimpleDataDTO import com.remax.visualnovel.repository.api.base.BaseRepositoryNew import com.remax.visualnovel.ui.wallet.manager.WalletManager +import com.remax.visualnovel.utils.FileUtil +import okhttp3.MediaType.Companion.toMediaType +import okhttp3.RequestBody +import okhttp3.RequestBody.Companion.toRequestBody import javax.inject.Inject @@ -31,6 +37,8 @@ class ChatRepository @Inject constructor(private val chatService: ChatService) : // ------------------------ new --------------------------------- + + suspend fun getSoundList(param: ParamSoundList) = executeHttp { chatService.requestSoundList(param) } @@ -39,14 +47,23 @@ class ChatRepository @Inject constructor(private val chatService: ChatService) : chatService.requestAiModelList(language) } - suspend fun getChatBgList(userId: Int) = executeHttp { + suspend fun getChatBgList(userId: ParamUserid) = executeHttp { chatService.requestChatBgList(userId) } - suspend fun uploadCustomBgPic(param: ParamBgUpload) = executeHttp { - chatService.uploadCustomBgPic(param) + + suspend fun uploadCustomBgPic( + fileUri: Uri, + param: ParamBgUpload + ) = executeHttp { + /*val file = fileUri.toFile()?: + return ApiFailedResponse(1, message = "File not exist")*/ + + val params = mutableMapOf() + params["userId"] = param.userId.toRequestBody(("text/plain").toMediaType()) + val filePart = FileUtil.createFilePart("file", fileUri.toFile()) + chatService.uploadCustomBgPic(params, filePart) } - } \ No newline at end of file diff --git a/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/ChatActivity.kt b/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/ChatActivity.kt index 4875710..1ea836f 100644 --- a/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/ChatActivity.kt +++ b/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/ChatActivity.kt @@ -2,6 +2,7 @@ package com.remax.visualnovel.ui.chat import android.graphics.Point +import android.net.Uri import android.view.View.GONE import android.view.View.VISIBLE import androidx.activity.viewModels @@ -97,7 +98,7 @@ class ChatActivity : BaseBindingActivity() { private fun loadChantBgDatas() { launchAndCollect2({ - mViewModel.loadChatBgList(1) + mViewModel.loadChatBgList(ParamUserid(1)) }) { onSuccess = { val dataList = it?: emptyList() @@ -129,6 +130,20 @@ class ChatActivity : BaseBindingActivity() { } } + private fun uploadCustomBg(file: Uri) { + launchAndCollect2({ + mViewModel.uploadCustomBgPic(1, file) + }) { + onSuccess = { + val dataList = it + } + + onComplete = { + + } + } + } + private val loginObserver = Observer { launchWithRequest({ //TODO - business handling for login events @@ -174,6 +189,10 @@ class ChatActivity : BaseBindingActivity() { override fun onSoundFiltersChanged(sexValue: Int) { loadSoundDatas(sexValue) } + + override fun onUploadCustomBg(file: Uri) { + uploadCustomBg(file) + } }) } } diff --git a/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/ChatViewModel.kt b/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/ChatViewModel.kt index 8b47320..206b18a 100644 --- a/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/ChatViewModel.kt +++ b/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/ChatViewModel.kt @@ -1,6 +1,7 @@ package com.remax.visualnovel.ui.chat +import android.net.Uri import com.remax.visualnovel.app.viewmodel.base.OssViewModel import com.remax.visualnovel.entity.imbean.raw.CustomRawData import com.remax.visualnovel.entity.request.ChatSetting @@ -89,8 +90,9 @@ class ChatViewModel @Inject constructor( //------------------------ new ------------------------ suspend fun loadSoundList(param: ParamSoundList) = chatRepository.getSoundList(param) suspend fun loadAiModelList(language: ParamLanguage) = chatRepository.getAiModelList(language) - suspend fun loadChatBgList(userId: Int) = chatRepository.getChatBgList(userId) - suspend fun uploadCustomBgPic(param: ParamBgUpload) = chatRepository.uploadCustomBgPic(param) + suspend fun loadChatBgList(userId: ParamUserid) = chatRepository.getChatBgList(userId) + suspend fun uploadCustomBgPic(userId: Int, file: Uri) = chatRepository.uploadCustomBgPic(file, ParamBgUpload(userId.toString())) + diff --git a/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/ChatSettingView.kt b/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/ChatSettingView.kt index a4844d4..38a13ad 100644 --- a/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/ChatSettingView.kt +++ b/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/ChatSettingView.kt @@ -3,6 +3,7 @@ package com.remax.visualnovel.ui.chat.setting.customui import android.content.Context import android.graphics.Color +import android.net.Uri import android.util.AttributeSet import android.view.LayoutInflater import android.view.View @@ -18,6 +19,7 @@ import com.remax.visualnovel.entity.response.ChatMode import com.remax.visualnovel.entity.response.ChatSound import com.remax.visualnovel.extension.showConfirmDialog import com.remax.visualnovel.ui.chat.setting.customui.expandableSelector.ExpandAiModelSelectView +import com.remax.visualnovel.ui.chat.setting.customui.expandableSelector.ExpandBackgroundSubView import com.remax.visualnovel.ui.chat.setting.customui.expandableSelector.ExpandBubbleSelectView import com.remax.visualnovel.ui.chat.setting.customui.expandableSelector.ExpandChatModeSelectView import com.remax.visualnovel.ui.chat.setting.customui.expandableSelector.ExpandSoundSelectView @@ -34,6 +36,7 @@ class ChatSettingView @JvmOverloads constructor( private lateinit var mEventListener: IEventListener interface IEventListener { fun onSoundFiltersChanged(sexValue: Int) + fun onUploadCustomBg(file: Uri) } fun setEventListener(listener: IEventListener) { mEventListener = listener @@ -320,6 +323,11 @@ class ChatSettingView @JvmOverloads constructor( ) mBinding.backgroundSelectorView.setItems(items) + mBinding.backgroundSelectorView.setOnEventListener(object: ExpandBackgroundSubView.IEventListener { + override fun onUploadCustomBg(file: Uri) { + mEventListener.onUploadCustomBg(file) + } + }) } diff --git a/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/expandableSelector/ExpandBackgroundSubView.kt b/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/expandableSelector/ExpandBackgroundSubView.kt index 3bf2948..91ac8ac 100644 --- a/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/expandableSelector/ExpandBackgroundSubView.kt +++ b/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/expandableSelector/ExpandBackgroundSubView.kt @@ -2,6 +2,7 @@ package com.remax.visualnovel.ui.chat.setting.customui.expandableSelector import android.annotation.SuppressLint import android.content.Context +import android.net.Uri import android.util.AttributeSet import android.view.LayoutInflater import android.widget.LinearLayout @@ -17,6 +18,7 @@ import com.remax.visualnovel.R import com.remax.visualnovel.databinding.LayoutItemSettingBackgroundBinding import com.remax.visualnovel.databinding.LayoutSettingBgSubViewBinding import com.remax.visualnovel.entity.response.ChatBackgroundBase +import com.remax.visualnovel.entity.response.ChatBubble import com.remax.visualnovel.extension.glide.load import com.remax.visualnovel.extension.toast import com.remax.visualnovel.utils.imagepick.EpalPickerPresenter @@ -39,6 +41,15 @@ class ExpandBackgroundSubView @JvmOverloads constructor( private var items = mutableListOf() private var mBinding: LayoutSettingBgSubViewBinding + private var mEventListener: IEventListener? = null + interface IEventListener { + fun onUploadCustomBg(file: Uri) + } + + fun setOnEventListener(listener: IEventListener) { + this.mEventListener = listener + } + init { mBinding = LayoutSettingBgSubViewBinding.inflate(LayoutInflater.from(context), this, true) @@ -132,7 +143,7 @@ class ExpandBackgroundSubView @JvmOverloads constructor( activity?.toast(error?.message) } - override fun onImagePickComplete(items: ArrayList?) { + override fun onImagePickComplete(items: ArrayList) { appendCustomBg(items) uploadImageAndRequest(items) } @@ -160,7 +171,9 @@ class ExpandBackgroundSubView @JvmOverloads constructor( } private fun uploadImageAndRequest(items: ArrayList?) { - // TODO + if (items != null && items.isNotEmpty()) { + mEventListener?.onUploadCustomBg(items.get(0)!!.uri) + } } diff --git a/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/expandableSelector/ExpandBubbleSelectView.kt b/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/expandableSelector/ExpandBubbleSelectView.kt index 9059d17..609a74f 100644 --- a/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/expandableSelector/ExpandBubbleSelectView.kt +++ b/VisualNovel/app/src/main/java/com/remax/visualnovel/ui/chat/setting/customui/expandableSelector/ExpandBubbleSelectView.kt @@ -25,7 +25,6 @@ class ExpandBubbleSelectView @JvmOverloads constructor( private var isExpanded = false private var animationDuration = 300 private var mEventListener: IEventListener? = null - interface IEventListener { fun onItemSelected(position: Int, item: ChatBubble) fun onExpanded(isExpanded: Boolean) diff --git a/VisualNovel/app/src/main/java/com/remax/visualnovel/utils/FileUtil.kt b/VisualNovel/app/src/main/java/com/remax/visualnovel/utils/FileUtil.kt new file mode 100644 index 0000000..55b283b --- /dev/null +++ b/VisualNovel/app/src/main/java/com/remax/visualnovel/utils/FileUtil.kt @@ -0,0 +1,64 @@ +package com.remax.visualnovel.utils + + + +import android.net.Uri +import com.remax.visualnovel.configs.NovelApplication +import okhttp3.MediaType.Companion.toMediaType +import okhttp3.MultipartBody +import okhttp3.RequestBody.Companion.asRequestBody +import java.io.File + +object FileUtil { + + private val appContext = NovelApplication.appContext() + + + + + private fun getFileFromUri(uri: Uri): File? { + return try { + when (uri.scheme) { + "file" -> File(uri.path!!) + "content" -> { + val inputStream = appContext.contentResolver.openInputStream(uri) + val file = File.createTempFile("upload_", null, appContext.cacheDir) + inputStream?.use { input -> + file.outputStream().use { output -> + input.copyTo(output) + } + } + file + } + else -> null + } + } catch (e: Exception) { + null + } + } + + fun createFilePart(partName: String, file: File): MultipartBody.Part { + val mediaType = getMimeType(file) + return MultipartBody.Part.createFormData( + partName, + file.name, + file.asRequestBody(mediaType.toMediaType()) + ) + } + + private fun getMimeType(file: File): String { + return when (file.extension.lowercase()) { + "jpg", "jpeg" -> "image/jpeg" + "png" -> "image/png" + "pdf" -> "application/pdf" + "mp4" -> "video/mp4" + else -> "application/octet-stream" + } + } + + + //==================== 扩展函数 ==================== + val Uri.toFile: File? + get() = FileUtil.getFileFromUri(this) + +} \ No newline at end of file