From fbad5f9d985810735854474a8d7b0785324aadb8 Mon Sep 17 00:00:00 2001 From: klaus Date: Wed, 11 Oct 2023 02:49:52 +0900 Subject: [PATCH] =?UTF-8?q?=EC=B1=84=EA=B8=88=20=EA=B8=B0=EB=8A=A5=20?= =?UTF-8?q?=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../co/vividnext/sodalive/common/Constants.kt | 1 + .../common/SharedPreferenceManager.kt | 16 +++ .../sodalive/live/room/LiveRoomActivity.kt | 123 +++++++++++++++++- .../live/room/LiveRoomNoChattingDialog.kt | 58 +++++++++ .../sodalive/live/room/LiveRoomRequestType.kt | 1 + .../room/profile/LiveRoomProfileAdapter.kt | 4 + .../room/profile/LiveRoomProfileDialog.kt | 2 + .../live/room/profile/LiveRoomProfileItem.kt | 14 ++ .../room/profile/LiveRoomUserProfileDialog.kt | 11 ++ .../res/layout/dialog_live_no_chatting.xml | 105 +++++++++++++++ .../layout/dialog_live_room_user_profile.xml | 13 ++ .../layout/item_live_room_list_profile.xml | 16 ++- 12 files changed, 362 insertions(+), 2 deletions(-) create mode 100644 app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomNoChattingDialog.kt create mode 100644 app/src/main/res/layout/dialog_live_no_chatting.xml diff --git a/app/src/main/java/kr/co/vividnext/sodalive/common/Constants.kt b/app/src/main/java/kr/co/vividnext/sodalive/common/Constants.kt index 015812b..b73f866 100644 --- a/app/src/main/java/kr/co/vividnext/sodalive/common/Constants.kt +++ b/app/src/main/java/kr/co/vividnext/sodalive/common/Constants.kt @@ -8,6 +8,7 @@ object Constants { const val PREF_IS_ADULT = "pref_is_adult" const val PREF_NICKNAME = "pref_nickname" const val PREF_USER_ROLE = "pref_user_role" + const val PREF_NO_CHAT_ROOM = "pref_no_chat" const val PREF_PUSH_TOKEN = "pref_push_token" const val PREF_PROFILE_IMAGE = "pref_profile_image" const val PREF_IS_CONTENT_PLAY_LOOP = "pref_is_content_play_loop" diff --git a/app/src/main/java/kr/co/vividnext/sodalive/common/SharedPreferenceManager.kt b/app/src/main/java/kr/co/vividnext/sodalive/common/SharedPreferenceManager.kt index faea416..02ddf57 100644 --- a/app/src/main/java/kr/co/vividnext/sodalive/common/SharedPreferenceManager.kt +++ b/app/src/main/java/kr/co/vividnext/sodalive/common/SharedPreferenceManager.kt @@ -3,6 +3,8 @@ package kr.co.vividnext.sodalive.common import android.content.Context import android.content.SharedPreferences import androidx.preference.PreferenceManager +import com.google.gson.Gson +import com.google.gson.reflect.TypeToken import kr.co.vividnext.sodalive.settings.notification.MemberRole object SharedPreferenceManager { @@ -122,4 +124,18 @@ object SharedPreferenceManager { set(value) { sharedPreferences[Constants.PREF_IS_VIEWED_ON_BOARDING_TUTORIAL] = value } + + var noChatRoomList: List + get() { + val list = sharedPreferences[Constants.PREF_NO_CHAT_ROOM, ""] + val gson = Gson() + val listType = object : TypeToken>() {}.type + val myList = gson.fromJson>(list, listType) + return myList ?: emptyList() + } + set(value) { + val gson = Gson() + val listJson = gson.toJson(value) + sharedPreferences[Constants.PREF_NO_CHAT_ROOM] = listJson + } } diff --git a/app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomActivity.kt b/app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomActivity.kt index 2cdc32e..ef7f785 100644 --- a/app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomActivity.kt +++ b/app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomActivity.kt @@ -11,6 +11,7 @@ import android.graphics.Rect import android.net.Uri import android.os.Build import android.os.Bundle +import android.os.CountDownTimer import android.os.Handler import android.os.Looper import android.text.Spannable @@ -107,6 +108,57 @@ class LiveRoomActivity : BaseActivity(ActivityLiveRoomB private var isSpeaker = false private var isSpeakerFold = false + private var isNoChatting = false + private var remainingNoChattingTime = noChattingTime + + private val countDownTimer = object : CountDownTimer(remainingNoChattingTime * 1000, 1000) { + override fun onTick(millisUntilFinished: Long) { + remainingNoChattingTime -= 1 + } + + override fun onFinish() { + isNoChatting = false + remainingNoChattingTime = noChattingTime + removeNoChatRoom() + Toast.makeText( + applicationContext, + "채팅금지가 해제되었습니다.", + Toast.LENGTH_SHORT + ).show() + } + } + + private fun startNoChatting() { + hideKeyboard { + binding.etChat.clearFocus() + + isNoChatting = true + Toast.makeText( + applicationContext, + "${viewModel.getManagerNickname()}님이 3분간 채팅을 금지하였습니다.", + Toast.LENGTH_SHORT + ).show() + countDownTimer.start() + } + } + + private fun addNoChatRoom() { + val noChatRoomList = SharedPreferenceManager.noChatRoomList.toMutableList() + noChatRoomList.add(roomId) + SharedPreferenceManager.noChatRoomList = noChatRoomList + } + + private fun removeNoChatRoom() { + val noChatRoomList = SharedPreferenceManager.noChatRoomList.toMutableList() + noChatRoomList.remove(roomId) + SharedPreferenceManager.noChatRoomList = noChatRoomList + } + + private fun containNoChatRoom(): Boolean { + val noChatRoomList = SharedPreferenceManager.noChatRoomList + return noChatRoomList.contains(roomId) + } + private val onBackPressedCallback = object : OnBackPressedCallback(true) { override fun handleOnBackPressed() { onClickQuit() @@ -150,6 +202,17 @@ class LiveRoomActivity : BaseActivity(ActivityLiveRoomB viewModel.getMemberCan() viewModel.getRoomInfo(roomId) + + binding.etChat.setOnFocusChangeListener { view, hasFocus -> + if (isNoChatting && hasFocus) { + Toast.makeText( + applicationContext, + "${remainingNoChattingTime}초 동안 채팅하실 수 없습니다", + Toast.LENGTH_SHORT + ).show() + view.clearFocus() + } + } } override fun onStart() { @@ -232,6 +295,15 @@ class LiveRoomActivity : BaseActivity(ActivityLiveRoomB changeListenerMessage(memberId) }, + onClickNoChatting = { userId, nickname, profileUrl -> + LiveRoomNoChattingDialog( + activity = this, + layoutInflater = layoutInflater, + nickname = nickname, + profileUrl = profileUrl, + confirmButtonClick = { setNoChatting(userId, nickname) } + ).show(screenWidth) + }, onClickKickOut = { LiveDialog( activity = this, @@ -304,6 +376,15 @@ class LiveRoomActivity : BaseActivity(ActivityLiveRoomB cancelButtonClick = {} ).show(screenWidth) }, + onClickNoChatting = { userId, nickname, profileUrl -> + LiveRoomNoChattingDialog( + activity = this, + layoutInflater = layoutInflater, + nickname = nickname, + profileUrl = profileUrl, + confirmButtonClick = { setNoChatting(userId, nickname) } + ).show(screenWidth) + }, onClickPopupMenu = { userId, nickname, isBlock, view -> showOptionMenu( this, @@ -398,6 +479,7 @@ class LiveRoomActivity : BaseActivity(ActivityLiveRoomB agora.deInitAgoraEngine() } } + countDownTimer.cancel() super.onDestroy() } @@ -967,6 +1049,17 @@ class LiveRoomActivity : BaseActivity(ActivityLiveRoomB } } + private fun setNoChatting(userId: Long, nickname: String) { + agora.sendRawMessageToPeer( + receiverUid = userId.toString(), + requestType = LiveRoomRequestType.NO_CHATTING + ) { + handler.post { + showDialog(content = "${nickname}님을 3분간 채팅금지를 하였습니다.") + } + } + } + private fun showDialog( content: String, cancelTitle: String = "", @@ -1008,7 +1101,13 @@ class LiveRoomActivity : BaseActivity(ActivityLiveRoomB val profileUrl = viewModel.getUserProfileUrl(SharedPreferenceManager.userId.toInt()) val rank = viewModel.getUserRank(SharedPreferenceManager.userId) - if (binding.etChat.text.isNotBlank() && nickname.isNotBlank() && profileUrl.isNotBlank()) { + if (isNoChatting) { + Toast.makeText( + applicationContext, + "${remainingNoChattingTime}초 동안 채팅하실 수 없습니다", + Toast.LENGTH_SHORT + ).show() + } else if (binding.etChat.text.isNotBlank() && nickname.isNotBlank() && profileUrl.isNotBlank()) { val message = binding.etChat.text.toString() chatAdapter.items.add( LiveRoomNormalChat( @@ -1086,6 +1185,8 @@ class LiveRoomActivity : BaseActivity(ActivityLiveRoomB } private fun joinChannel(roomInfo: GetRoomInfoResponse) { + loadingDialog.show(width = screenWidth, message = "라이브에 입장하고 있습니다.") + val userId = SharedPreferenceManager.userId agora.joinRtcChannel( uid = userId.toInt(), @@ -1194,6 +1295,10 @@ class LiveRoomActivity : BaseActivity(ActivityLiveRoomB } }, rtmChannelJoinSuccess = { + handler.post { + loadingDialog.dismiss() + } + if (userId == roomInfo.creatorId) { setBroadcaster() } else { @@ -1208,6 +1313,10 @@ class LiveRoomActivity : BaseActivity(ActivityLiveRoomB } else { startService(intent) } + + if (containNoChatRoom()) { + startNoChatting() + } }, rtmChannelJoinFail = { agoraConnectFail() @@ -1402,7 +1511,19 @@ class LiveRoomActivity : BaseActivity(ActivityLiveRoomB viewModel.getRoomInfo(roomId = roomId) return } + + if (rawMessage == LiveRoomRequestType.NO_CHATTING.toString() && !isNoChatting) { + handler.post { + addNoChatRoom() + startNoChatting() + } + return + } } } } + + companion object { + private const val noChattingTime = 180L + } } diff --git a/app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomNoChattingDialog.kt b/app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomNoChattingDialog.kt new file mode 100644 index 0000000..351a7c2 --- /dev/null +++ b/app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomNoChattingDialog.kt @@ -0,0 +1,58 @@ +package kr.co.vividnext.sodalive.live.room + +import android.app.Activity +import android.graphics.Color +import android.graphics.drawable.ColorDrawable +import android.view.LayoutInflater +import android.view.WindowManager +import androidx.appcompat.app.AlertDialog +import coil.load +import coil.transform.CircleCropTransformation +import kr.co.vividnext.sodalive.R +import kr.co.vividnext.sodalive.databinding.DialogLiveNoChattingBinding +import kr.co.vividnext.sodalive.extensions.dpToPx + +class LiveRoomNoChattingDialog( + activity: Activity, + layoutInflater: LayoutInflater, + nickname: String, + profileUrl: String, + confirmButtonClick: () -> Unit, +) { + + private val alertDialog: AlertDialog + + val dialogView = DialogLiveNoChattingBinding.inflate(layoutInflater) + + init { + val dialogBuilder = AlertDialog.Builder(activity) + dialogBuilder.setView(dialogView.root) + + alertDialog = dialogBuilder.create() + alertDialog.setCancelable(false) + alertDialog.window?.setBackgroundDrawable(ColorDrawable(Color.TRANSPARENT)) + + dialogView.tvConfirm.setOnClickListener { + alertDialog.dismiss() + confirmButtonClick() + } + + dialogView.tvNickname.text = nickname + dialogView.ivProfile.load(profileUrl) { + crossfade(true) + placeholder(R.drawable.bg_placeholder) + transformations(CircleCropTransformation()) + } + } + + fun show(width: Int) { + alertDialog.show() + + val lp = WindowManager.LayoutParams() + lp.copyFrom(alertDialog.window?.attributes) + lp.width = width - (26.7f.dpToPx()).toInt() + lp.height = WindowManager.LayoutParams.WRAP_CONTENT + + alertDialog.window?.attributes = lp + } +} diff --git a/app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomRequestType.kt b/app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomRequestType.kt index baabfe6..56bf074 100644 --- a/app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomRequestType.kt +++ b/app/src/main/java/kr/co/vividnext/sodalive/live/room/LiveRoomRequestType.kt @@ -8,4 +8,5 @@ enum class LiveRoomRequestType { @SerializedName("KICK_OUT") KICK_OUT, @SerializedName("SET_MANAGER") SET_MANAGER, @SerializedName("RELEASE_MANAGER") RELEASE_MANAGER, + @SerializedName("NO_CHATTING") NO_CHATTING, } diff --git a/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileAdapter.kt b/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileAdapter.kt index 491eee6..03993ea 100644 --- a/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileAdapter.kt +++ b/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileAdapter.kt @@ -15,6 +15,7 @@ class LiveRoomProfileAdapter( private val isStaff: () -> Boolean, private val onClickInviteSpeaker: (Long) -> Unit, private val onClickChangeListener: (Long) -> Unit, + private val onClickNoChatting: (Long, String, String) -> Unit, private val kickOut: (Long) -> Unit, private val onClickProfile: (Long) -> Unit ) : RecyclerView.Adapter() { @@ -164,6 +165,7 @@ class LiveRoomProfileAdapter( managerId = managerId, onClickInviteSpeaker = onClickInviteSpeaker, onClickChangeListener = onClickChangeListener, + onClickNoChatting = onClickNoChatting, kickOut = kickOut, onClickProfile = onClickProfile ) @@ -233,6 +235,7 @@ class LiveRoomProfileUserViewHolder( private val managerId: Long, private val onClickInviteSpeaker: (Long) -> Unit, private val onClickChangeListener: (Long) -> Unit, + private val onClickNoChatting: (Long, String, String) -> Unit, private val kickOut: (Long) -> Unit, private val onClickProfile: (Long) -> Unit ) : LiveRoomProfileViewHolder(binding) { @@ -241,6 +244,7 @@ class LiveRoomProfileUserViewHolder( item.managerId = managerId item.onClickInviteSpeaker = onClickInviteSpeaker item.onClickChangeListener = onClickChangeListener + item.onClickNoChatting = onClickNoChatting item.kickOut = kickOut item.onClickProfile = onClickProfile item.bind(binding) diff --git a/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileDialog.kt b/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileDialog.kt index b136bd6..1dc1b4c 100644 --- a/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileDialog.kt +++ b/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileDialog.kt @@ -17,6 +17,7 @@ class LiveRoomProfileDialog( onClickInviteSpeaker: (Long) -> Unit, onClickChangeListener: (Long) -> Unit, onClickKickOut: (Long) -> Unit, + onClickNoChatting: (Long, String, String) -> Unit, onClickProfile: (Long) -> Unit ) { private val bottomSheetDialog: BottomSheetDialog = BottomSheetDialog(activity) @@ -25,6 +26,7 @@ class LiveRoomProfileDialog( isStaff = isStaff, onClickInviteSpeaker = onClickInviteSpeaker, onClickChangeListener = onClickChangeListener, + onClickNoChatting = onClickNoChatting, kickOut = onClickKickOut, onClickProfile = onClickProfile ) diff --git a/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileItem.kt b/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileItem.kt index 8fa477e..d7d1149 100644 --- a/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileItem.kt +++ b/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomProfileItem.kt @@ -42,6 +42,7 @@ abstract class LiveRoomProfileItem { open var managerId = 0L open var onClickInviteSpeaker: (Long) -> Unit = {} open var onClickChangeListener: (Long) -> Unit = {} + open var onClickNoChatting: (Long, String, String) -> Unit = { _, _, _ -> } open var kickOut: (Long) -> Unit = {} open var onClickProfile: (Long) -> Unit = {} abstract fun bind(binding: ViewBinding) @@ -197,5 +198,18 @@ data class LiveRoomProfileItemUser( } else { itemBinding.llControlButtons.visibility = View.GONE } + + if (managerId == SharedPreferenceManager.userId) { + itemBinding.tvNoChatting.visibility = View.VISIBLE + itemBinding.tvNoChatting.setOnClickListener { + onClickNoChatting( + id, + nickname, + profileUrl + ) + } + } else { + itemBinding.tvNoChatting.visibility = View.GONE + } } } diff --git a/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomUserProfileDialog.kt b/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomUserProfileDialog.kt index 6ebbaea..2119920 100644 --- a/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomUserProfileDialog.kt +++ b/app/src/main/java/kr/co/vividnext/sodalive/live/room/profile/LiveRoomUserProfileDialog.kt @@ -28,6 +28,7 @@ class LiveRoomUserProfileDialog( private val onClickInviteSpeaker: (Long) -> Unit, private val onClickChangeListener: (Long) -> Unit, private val onClickKickOut: (Long) -> Unit, + private val onClickNoChatting: (Long, String, String) -> Unit, private val onClickPopupMenu: (Long, String, Boolean, View) -> Unit, ) { private val alertDialog: AlertDialog @@ -128,6 +129,7 @@ class LiveRoomUserProfileDialog( if (userProfile.isManager != null) { dialogView.tvSetManager.visibility = View.VISIBLE + dialogView.tvNoChatting.visibility = View.VISIBLE if (userProfile.isManager) { dialogView.tvSetManager.text = "스탭 해제" @@ -142,8 +144,17 @@ class LiveRoomUserProfileDialog( alertDialog.dismiss() } } + + dialogView.tvNoChatting.setOnClickListener { + onClickNoChatting( + userProfile.userId, + userProfile.nickname, + userProfile.profileUrl + ) + } } else { dialogView.tvSetManager.visibility = View.GONE + dialogView.tvNoChatting.visibility = View.GONE } if ( diff --git a/app/src/main/res/layout/dialog_live_no_chatting.xml b/app/src/main/res/layout/dialog_live_no_chatting.xml new file mode 100644 index 0000000..ae187e3 --- /dev/null +++ b/app/src/main/res/layout/dialog_live_no_chatting.xml @@ -0,0 +1,105 @@ + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/layout/dialog_live_room_user_profile.xml b/app/src/main/res/layout/dialog_live_room_user_profile.xml index 0e0d997..87f728b 100644 --- a/app/src/main/res/layout/dialog_live_room_user_profile.xml +++ b/app/src/main/res/layout/dialog_live_room_user_profile.xml @@ -215,6 +215,19 @@ android:visibility="gone" /> + + + + -