优化列表更新和红点显示

This commit is contained in:
squallzhjch 2023-01-09 16:29:58 +08:00
parent 13f3516566
commit 7b5b4b08e5
8 changed files with 118 additions and 58 deletions

View File

@ -9,6 +9,8 @@ class Constant {
*/
const val SERVER_ADDRESS = "http://ec2-52-81-73-5.cn-north-1.compute.amazonaws.com.cn:8088/"
val DEBUG = Boolean.parseBoolean("true")
const val message_status_late = "预约,待发送"
}
}

View File

@ -1,8 +1,39 @@
package com.navinfo.volvo
import android.app.Activity
import android.app.Application
import android.content.pm.ActivityInfo
import android.os.Bundle
import dagger.hilt.android.HiltAndroidApp
@HiltAndroidApp
open class MyApplication : Application() {
override fun onCreate() {
super.onCreate()
registerActivityLifecycleCallbacks(object : ActivityLifecycleCallbacks {
override fun onActivityCreated(activity: Activity, savedInstanceState: Bundle?) {
activity?.requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_PORTRAIT
}
override fun onActivityStarted(activity: Activity) {
}
override fun onActivityResumed(activity: Activity) {
}
override fun onActivityPaused(activity: Activity) {
}
override fun onActivityStopped(activity: Activity) {
}
override fun onActivitySaveInstanceState(activity: Activity, outState: Bundle) {
}
override fun onActivityDestroyed(activity: Activity) {
}
})
}
}

View File

@ -1,7 +1,9 @@
package com.navinfo.volvo.database.dao
import android.util.Log
import androidx.paging.PagingSource
import androidx.room.*
import com.navinfo.volvo.Constant
import com.navinfo.volvo.database.entity.GreetingMessage
import kotlinx.coroutines.flow.Flow
@ -20,7 +22,7 @@ interface GreetingMessageDao {
/**
* 未读消息统计
*/
@Query("SELECT count(id) FROM GreetingMessage WHERE read = 0")
@Query("SELECT count(id) FROM GreetingMessage WHERE status = '${Constant.message_status_late}'")
fun countUnreadByFlow(): Flow<Long>
/**
@ -32,8 +34,8 @@ interface GreetingMessageDao {
/**
* 检查某条数据是否存在
*/
@Query("SELECT id From GreetingMessage WHERE id = :id LIMIT 1")
suspend fun getMessageId(id: Long): Long
@Query("SELECT uuid From GreetingMessage WHERE id = :id LIMIT 1")
suspend fun getMessageId(id: Long): Long?
/**
*
@ -41,12 +43,18 @@ interface GreetingMessageDao {
@Transaction
suspend fun insertOrUpdate(list: List<GreetingMessage>) {
for (message in list) {
val id = getMessageId(message.id)
if (id == 0L) {
insert(message)
Log.e("jingo", "insertOrUpdate ${message.id}")
val uuid = getMessageId(message.id)
Log.e("jingo", "insertOrUpdate $uuid")
if (uuid == null || uuid == 0L) {
Log.e("jingo", "insertOrUpdate start ")
val l = insert(message)
Log.e("jingo", "insertOrUpdate $l ")
} else {
message.uuid = uuid
update(message)
}
Log.e("jingo", "insertOrUpdate end")
}
}

View File

@ -57,7 +57,7 @@ class HomeAdapter(fragment: Fragment) :
class DiffCallback : DiffUtil.ItemCallback<GreetingMessage>() {
override fun areItemsTheSame(oldItem: GreetingMessage, newItem: GreetingMessage): Boolean {
return oldItem.uuid == newItem.uuid
return oldItem.uuid == newItem.uuid && oldItem.status == newItem.status
}
override fun areContentsTheSame(

View File

@ -12,6 +12,7 @@ import androidx.lifecycle.lifecycleScope
import androidx.paging.LoadState
import androidx.recyclerview.widget.DividerItemDecoration
import androidx.recyclerview.widget.LinearLayoutManager
import com.easytools.tools.ThreadPoolUtils.runOnUiThread
import com.navinfo.volvo.R
import com.navinfo.volvo.databinding.FragmentHomeBinding
import com.navinfo.volvo.databinding.HomeAdapterNotingBinding
@ -21,6 +22,7 @@ import com.navinfo.volvo.ui.fragments.BaseFragment
import com.yanzhenjie.recyclerview.*
import dagger.hilt.android.AndroidEntryPoint
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import java.io.IOException
@AndroidEntryPoint
@ -55,19 +57,19 @@ class HomeFragment : BaseFragment(), OnItemClickListener, OnItemMenuClickListene
var mSwipeMenuCreator = SwipeMenuCreator { _, rightMenu, _ ->
//添加菜单自动添加至尾部
var deleteItem = SwipeMenuItem(context)
deleteItem.height = DisplayUtil.dip2px(context!!, 60f)
deleteItem.width = DisplayUtil.dip2px(context!!, 80f)
deleteItem.background = context!!.getDrawable(R.color.red)
deleteItem.text = context!!.getString(R.string.delete)
deleteItem.height = DisplayUtil.dip2px(requireContext(), 60f)
deleteItem.width = DisplayUtil.dip2px(requireContext(), 80f)
deleteItem.background = requireContext().getDrawable(R.color.red)
deleteItem.text = requireContext().getString(R.string.delete)
rightMenu.addMenuItem(deleteItem)
//分享
var shareItem = SwipeMenuItem(context)
shareItem.height = DisplayUtil.dip2px(context!!, 60f)
shareItem.width = DisplayUtil.dip2px(context!!, 80f)
shareItem.background = context!!.getDrawable(R.color.gray)
shareItem.text = context!!.getString(R.string.share)
shareItem.setTextColor(R.color.white)
shareItem.height = DisplayUtil.dip2px(requireContext(), 60f)
shareItem.width = DisplayUtil.dip2px(requireContext(), 80f)
shareItem.background = requireContext().getDrawable(R.color.gray)
shareItem.text = requireContext().getString(R.string.share)
shareItem.setTextColor(requireContext().getColor(R.color.white))
rightMenu.addMenuItem(shareItem)
}
//侧滑按钮
@ -123,11 +125,14 @@ class HomeFragment : BaseFragment(), OnItemClickListener, OnItemMenuClickListene
messageAdapter.addLoadStateListener {
when (it.refresh) {
is LoadState.NotLoading -> {
binding.homeRecyclerview.addHeaderView(headBinding!!.root)
if (messageAdapter.itemCount == 0)
binding.homeRecyclerview.addHeaderView(headBinding!!.root)
else{
binding.homeRecyclerview.removeHeaderView(headBinding!!.root)
}
Log.d("jingo", "is NotLoading")
}
is LoadState.Loading -> {
binding.homeRecyclerview.removeHeaderView(headBinding!!.root)
Log.d("jingo", "is Loading")
}
is LoadState.Error -> {

View File

@ -7,7 +7,8 @@ import android.text.TextUtils
import android.view.LayoutInflater
import android.view.MotionEvent
import android.view.View
import android.view.View.*
import android.view.View.GONE
import android.view.View.VISIBLE
import android.view.ViewGroup
import android.widget.AdapterView
import android.widget.AdapterView.OnItemSelectedListener
@ -18,17 +19,9 @@ import androidx.core.widget.addTextChangedListener
import androidx.fragment.app.Fragment
import androidx.fragment.app.viewModels
import androidx.lifecycle.Observer
import androidx.lifecycle.ViewModel
import androidx.lifecycle.ViewModelProvider
import androidx.lifecycle.lifecycleScope
import androidx.navigation.Navigation
import androidx.navigation.fragment.findNavController
import com.easytools.tools.DateUtils
import com.easytools.tools.DisplayUtils
import com.easytools.tools.FileIOUtils
import com.easytools.tools.ResourceUtils
import com.easytools.tools.ThreadPoolUtils.runOnUiThread
import com.easytools.tools.ToastUtils
import com.easytools.tools.*
import com.elvishew.xlog.XLog
import com.github.file_picker.FileType
import com.github.file_picker.ListDirection
@ -58,7 +51,6 @@ import com.nhaarman.supertooltips.ToolTip
import dagger.hilt.android.AndroidEntryPoint
import indi.liyi.viewer.Utils
import indi.liyi.viewer.ViewData
import kotlinx.coroutines.launch
import top.zibin.luban.Luban
import top.zibin.luban.OnCompressListener
import java.io.File
@ -196,8 +188,11 @@ class ObtainMessageFragment : Fragment() {
}
val sendToArray = mutableListOf<VolvoModel>(VolvoModel("XC60", "智雅", "LYVXFEFEXNL754427"))
binding.edtSendTo.adapter = ArrayAdapter<String>(requireContext(),
android.R.layout.simple_dropdown_item_1line, android.R.id.text1, sendToArray.stream().map { it -> "${it.version} ${it.model} ${it.num}" }.toList())
binding.edtSendTo.onItemSelectedListener = object: OnItemSelectedListener {
android.R.layout.simple_dropdown_item_1line,
android.R.id.text1,
sendToArray.stream().map { it -> "${it.version} ${it.model} ${it.num}" }.toList()
)
binding.edtSendTo.onItemSelectedListener = object : OnItemSelectedListener {
override fun onItemSelected(p0: AdapterView<*>?, p1: View?, p2: Int, p3: Long) {
obtainMessageViewModel.getMessageLiveData().value?.toWho = sendToArray[p2].num
}
@ -287,13 +282,23 @@ class ObtainMessageFragment : Fragment() {
// Do something here with selected files
val audioFile = files.get(0).file
if (!audioFile.parentFile.parentFile.absolutePath.equals(SystemConstant.SoundFolder)) {
val copyResult = FileIOUtils.writeFileFromIS(File(SystemConstant.SoundFolder, audioFile.name), FileInputStream(audioFile))
XLog.e("拷贝结果:"+copyResult)
val copyResult = FileIOUtils.writeFileFromIS(
File(
SystemConstant.SoundFolder,
audioFile.name
), FileInputStream(audioFile)
)
XLog.e("拷贝结果:" + copyResult)
if (!copyResult) {
ToastUtils.showToast("无法访问该文件,请重新选择其他文件")
return
}
obtainMessageViewModel.updateMessageAudio(File(SystemConstant.SoundFolder, audioFile.name).absolutePath)
obtainMessageViewModel.updateMessageAudio(
File(
SystemConstant.SoundFolder,
audioFile.name
).absolutePath
)
} else {
obtainMessageViewModel.updateMessageAudio(audioFile.absolutePath)
}
@ -306,7 +311,7 @@ class ObtainMessageFragment : Fragment() {
ToastUtils.showToast("只能选择.m4a文件")
return
}
if (media.file.length()>2*1000*1000) {
if (media.file.length() > 2 * 1000 * 1000) {
ToastUtils.showToast("文件不能超过2M")
return
}
@ -349,12 +354,13 @@ class ObtainMessageFragment : Fragment() {
false
}
MotionEvent.ACTION_UP -> {
if (System.currentTimeMillis() - startRecordTime<2000) {
if (System.currentTimeMillis() - startRecordTime < 2000) {
ToastUtils.showToast("录音时间太短!")
recorderLifecycleObserver.stopAndReleaseRecorder()
return
}
val recorderAudioPath = recorderLifecycleObserver.stopAndReleaseRecorder()
val recorderAudioPath =
recorderLifecycleObserver.stopAndReleaseRecorder()
if (File(recorderAudioPath).exists()) {
obtainMessageViewModel.updateMessageAudio(recorderAudioPath)
}
@ -408,25 +414,29 @@ class ObtainMessageFragment : Fragment() {
}
// 如果当前文件不在camera缓存文件夹下则移动该文件
if (!file!!.parentFile.absolutePath.equals(SystemConstant.CameraFolder)) {
val copyResult = FileIOUtils.writeFileFromIS(
File(
SystemConstant.CameraFolder,
fileName
), FileInputStream(file)
)
XLog.e("拷贝结果:" + copyResult)
// 跳转回原Fragment展示拍摄的照片
ViewModelProvider(requireActivity()).get(ObtainMessageViewModel::class.java)
.updateMessagePic(
try {
val copyResult = FileIOUtils.writeFileFromIS(
File(
SystemConstant.CameraFolder,
fileName
).absolutePath
), FileInputStream(file)
)
XLog.e("拷贝结果:$copyResult")
// 跳转回原Fragment展示拍摄的照片
obtainMessageViewModel
.updateMessagePic(
File(
SystemConstant.CameraFolder,
fileName
).absolutePath
)
} catch (e: Exception) {
XLog.e("崩溃:${e.message}")
}
} else {
// 跳转回原Fragment展示拍摄的照片
ViewModelProvider(requireActivity()).get(ObtainMessageViewModel::class.java)
.updateMessagePic(file!!.absolutePath)
obtainMessageViewModel.updateMessagePic(file!!.absolutePath)
}
}
@ -612,7 +622,7 @@ class ObtainMessageFragment : Fragment() {
val sendDate = DateUtils.str2Date(messageData?.sendDate, dateSendFormat)
val cal = Calendar.getInstance()
cal.time = Date()
cal.set(Calendar.MINUTE, cal.get(Calendar.MINUTE)+1)
cal.set(Calendar.MINUTE, cal.get(Calendar.MINUTE) + 1)
if (sendDate.time < cal.time.time) { // 发送时间设置小于当前时间1分钟后Toast提示用户并自动设置发送时间
messageData?.sendDate = DateUtils.date2Str(cal.time, dateSendFormat)
ToastUtils.showToast("自动调整发送时间为1分钟后发送")
@ -692,6 +702,7 @@ class ObtainMessageFragment : Fragment() {
})
.show()
}
fun onRecorderDenied() {
ToastUtils.showToast("当前操作需要您授权录音权限!")
}

View File

@ -27,13 +27,13 @@ import javax.inject.Inject
@HiltViewModel
class ObtainMessageViewModel @Inject constructor(
private val pre: PreferencesRepository
private val pre: PreferencesRepository,
) : ViewModel() {
private val msgLiveData: MutableLiveData<GreetingMessage> by lazy {
MutableLiveData<GreetingMessage>()
}
lateinit var username: String
var username: String = ""
init {
viewModelScope.launch {

View File

@ -1,12 +1,14 @@
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:tools="http://schemas.android.com/tools"
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools">
<data>
<import type="android.view.View" />
<import type="com.navinfo.volvo.Constant" />
<variable
name="greetingMessage"
type="com.navinfo.volvo.database.entity.GreetingMessage" />
@ -24,10 +26,10 @@
android:layout_marginLeft="8dp"
android:scaleType="fitXY"
android:src="@mipmap/ic_launcher"
app:roundPercent="0.4"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
app:layout_constraintTop_toTopOf="parent"
app:roundPercent="0.4" />
<TextView
android:id="@+id/message_badge"
@ -36,6 +38,7 @@
android:background="@drawable/shape_circular"
android:gravity="center"
android:textColor="#000000"
android:visibility="@{Constant.message_status_late.equals(greetingMessage.status)?View.VISIBLE:View.INVISIBLE}"
app:layout_constraintCircle="@id/message_head_icon"
app:layout_constraintCircleAngle="45"
app:layout_constraintCircleRadius="40dp"