I tried to run this code and every time I run it shows this result - api

private fun moveMarkerAnimation(key: String, newData: AnimationModel, marker: Marker?, from: String, to: String) {
if (!newData.isRun)
{
compositeDisposable.add(
iGoogleAPI.getDirections(
"driving",
"less_driving",
from, to,
getString(R.string.google_api_key1)
)!!.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe { returnResult ->
Log.d("API_RETURN",returnResult,)
try {
val jsonObject = JSONObject(returnResult)
val jsonArray = jsonObject.getJSONArray("routes")
for ( i in 0 until jsonArray.length())
{
val route = jsonArray.getJSONObject(i)
val poly = route.getJSONObject("overview_polyLine")
val polyLine = poly.getString("points")
polylineList = Common.decodePoly(polyLine) as java.util.ArrayList<LatLng?>
}
handler = Handler()
index = -1
next = 1
val runnable = object :Runnable{
override fun run() {
if (polylineList!!.size > 1)
{
if (index< polylineList!!.size)
{
index ++
next = index+1
start = polylineList!![index] !!
end = polylineList!![next]!!
}
val valueAnimator = ValueAnimator.ofInt(0,1)
valueAnimator.duration = 3000
valueAnimator.interpolator = LinearInterpolator()
valueAnimator.addUpdateListener { value ->
v = value.animatedFraction
lat = v*end !!.latitude + (1-v) * start!!.latitude
lng = v*end !!.longitude+ (1-v) * start!!.longitude
val newPos = LatLng(lat,lng)
marker!!.position = newPos
marker!!.setAnchor(0.5f,0.5f)
marker!!.rotation = Common.getBearing(start!!,newPos)
}
valueAnimator.start()
if (index < polylineList!!.size-2)
{
handler!!.postDelayed(this,1500)
}else if (index < polylineList!!.size-1)
{
newData.isRun = false
Common.driversSubscrib.put(key,newData)
}
}
}
}
handler!!.postDelayed(runnable,1500)
}
catch (e:java.lang.Exception){
Snackbar.make(requireView(),e.message!!,Snackbar.LENGTH_LONG).show()
}
When the site changes from from firebase this result appears
022-04-26 13:19:30.912 23482-23482/com.example.bustrackerriderapp E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.example.bustrackerriderapp, PID: 23482
io.reactivex.exceptions.OnErrorNotImplementedException: The exception was not handled due to missing onError handler in the subscribe() method call. Further reading
what should I do to fix this problem

Related

Remove redundant also calls

I'm working with TCP communication and use Ktor library.
I have packets that come, and the first byte is the packet's lengths.
Likewise, I read the packet from what is documented on the protocol API, and sometimes I have to skip the remaining bytes of the packet, so I subtract what I have read to this message length.
At the present time, I call also { messageLength -= length } on each reading, but the code is unreadable.
#Test
fun ktorTests() {
runBlocking {
val selectorManager = SelectorManager(Dispatchers.IO)
val socket = aSocket(selectorManager).tcp().connect("server.slsknet.org", 2242)
val openReadChannel = socket.openReadChannel()
val openWriteChannel = socket.openWriteChannel(autoFlush = true)
val login = "Test"
val pwd = "159753"
openWriteChannel.write {
it.put(
ByteMessage().writeInt32(1)
.writeStr(login)
.writeStr(pwd)
.writeInt32(160)
.writeStr((login + pwd).toMD5())
.writeInt32(1)
.getBuff()
)
}
while (true) {
var messageLength = openReadChannel.readIntLittleEndian()
val code = openReadChannel.readIntLittleEndian()
println("ServerClient received: Message code:" + code + " Packet Size:" + (messageLength + 4))
when (code) {
1 -> {
if (openReadChannel.readBoolean().also { messageLength -= 1 }) {
val greetingLength = openReadChannel.readIntLittleEndian().also { messageLength -= 4 }
val greeting = ByteArray(greetingLength)
openReadChannel.readFully(greeting, 0, greetingLength)
.also { messageLength -= greetingLength }
val ip = openReadChannel.readIntLittleEndian().also { messageLength -= 4 }
println("Logged In.")
}
openReadChannel.discardExact(messageLength.toLong())
}
}
}
Any ideas on ho could it be done ?

Get Address from current location Kotlin

I get the current location like this:
val fusedLocationClient: FusedLocationProviderClient =
LocationServices.getFusedLocationProviderClient(LocalContext.current)
fun getLastKnownLocation() {
fusedLocationClient.lastLocation.addOnSuccessListener { location ->
if (location != null) {
longitude.value = location.longitude
latitude.value = location.latitude
}
}
}
How I can get the Address from it?
Update
I implemented like this:
fun getLastKnownLocation() {
fusedLocationClient.lastLocation.addOnSuccessListener { location ->
if (location != null) {
longitude.value = location.longitude
latitude.value = location.latitude
val geocoder = Geocoder(app)
if (Build.VERSION.SDK_INT >= 33) {
geocoder.getFromLocation(
location.latitude, location.longitude, 1
) { addresses ->
address.value = addresses.first().toString()
}
}
else {
try {
val addresses = geocoder.getFromLocation(location.latitude, location.longitude, 1
)?.firstOrNull()
address.value = addresses.toString()
} catch (Exp: Exception) {
address.value = "No Address found"
println("$Exp")
}
}
}
}
}
But got this exception: java.io.IOException: eccc: DEADLINE_EXCEEDED: deadline exceeded after 4.907678698s
val geocoder = Geocoder(this, Locale.getDefault())
val addresses = geocoder.getFromLocation(location.latitude, location.longitude, 1)
https://developer.android.com/reference/kotlin/android/location/Geocoder

Google Places OpeningHours.getWeekdayText() is NULL for some locations

I'm using google places to retrieve information for a place such as the business name, address, OpenHours and LatLng.
This works 95% of the time, but for some places I receive the error...
"Attempt to invoke virtual method 'java.util.List com.google.android.libraries.places.api.model.OpeningHours.getWeekdayText()' on a null object reference"
Looking on Google maps, I do see these places have open hours information.
//Add a marker when a POI on map is clicked.
map.setOnPoiClickListener { poi ->
map.clear()
val poiMarker = map.addMarker(
MarkerOptions()
.position(poi.latLng)
.title(poi.name)
)
poiMarker?.showInfoWindow()
placeId = poi.placeId
Timber.i("Place ID: $placeId")
//https://developers.google.com/maps/documentation/places/android-sdk/reference/com/google/android/libraries/places/api/net/PlacesClient#fetchPlace(com.google.android.libraries.places.api.net.FetchPlaceRequest)
val placeFields = listOf(Place.Field.ID, Place.Field.NAME, Place.Field.ADDRESS, Place.Field.OPENING_HOURS, Place.Field.LAT_LNG)
val request = FetchPlaceRequest.newInstance(placeId, placeFields)
if (!Places.isInitialized()) {
Places.initialize(requireContext(), apiKey, Locale.US);
}
val placesClient = Places.createClient(requireContext())
placesClient.fetchPlace(request)
.addOnSuccessListener { response: FetchPlaceResponse ->
val place = response.place
setLiveDataPlace(place)
}.addOnFailureListener { exception: Exception ->
if (exception is ApiException) {
Timber.i( "Place not found: ${exception.message}")
}
}
binding.buttonSave.visibility = View.VISIBLE
}
}
fun setLiveDataPlace(place: Place){
placeId = place.id as String
placeName = place.name as String
placeAddress = place.address as String
try {
placeOpenMonday = place.openingHours.weekdayText[0]
placeOpenTuesday = place.openingHours.weekdayText[1]
placeOpenWednesday = place.openingHours.weekdayText[2]
placeOpenThursday = place.openingHours.weekdayText[3]
placeOpenFriday = place.openingHours.weekdayText[4]
placeOpenSaturday = place.openingHours.weekdayText[5]
placeOpenSunday = place.openingHours.weekdayText[6]
} catch(e : Exception) {
Timber.i("Open hours exception: ${e.message}")
}
placeLat = place.latLng.latitude.toString()
placeLng = place.latLng.longitude.toString()
Timber.i("Place: $place")
}

Alarm manager show notification every time when i open the app

I am using the requestj api to send and receive the data from server and setting up the alarm on time that i received from server and alarm calls two hours ago from received time but issue is that when alarm fire on exact time it also fire every time when api calls till that 2 hours didn't completed. Any one know how to prevent it?
1.API code is here
fun getAllFriendsReminders(context: Context) {
val getReminderHttpRequest = HttpRequest()
// val myList = ArrayList<FriendsRemindersListModel>()
getReminderHttpRequest.setOnResponseListener { getReminderListResponse ->
Log.e("getReminders List", getReminderListResponse.code.toString())
Log.e("getReminders List", getReminderListResponse.text)
if (getReminderListResponse.code == HttpResponse.HTTP_OK) {
Log.e("getReminders List", getReminderListResponse.code.toString())
val jsonArray = getReminderListResponse.toJSONArray()
getReminderListModel.clear()
Log.e("list", jsonArray.length().toString())
Log.e("list", jsonArray.toString())
val loggedInUser = appGlobals.getValueString("loginUsername")
for (i in 0 until jsonArray!!.length()) {
if (!onForeGround) {
progressBar!!.progress = i
}
Log.e("listi", i.toString())
val jsonObject = jsonArray.getJSONObject(i)
friendReminderText = jsonObject.getString("reminder")
friendReminderFromName = jsonObject.getString("reminder_from")
friendReminderToName = jsonObject.getString("reminder_to")
friendReminderDate = jsonObject.getString("date")
friendReminderStatus = jsonObject.getString("status")
friendReminderId = jsonObject.getString("id")
if (friendReminderFromName != loggedInUser) {
getReminderListModel.add(FriendsRemindersListModel(0, friendReminderId.toInt(),friendReminderText,
friendReminderDate, friendReminderFromName, friendReminderToName, friendReminderStatus))
//Received date time from server
val dateTimeFormatter = DateTimeFormatter.ofPattern("dd-MM-yyyy hh:mm:ss a")
// val dateFormatter = DateTimeFormatter.ofPattern("dd-MM-yyyy")
// val timeFormatter = DateTimeFormatter.ofPattern("hh:mm:ss a")
val instant = Instant.ofEpochMilli(friendReminderDate.toLong())
val instant1 = Instant.ofEpochMilli(friendReminderDate.toLong() - (120 * 60 * 1000))
val date = LocalDateTime.ofInstant(instant, ZoneId.systemDefault())
val date1 = LocalDateTime.ofInstant(instant1, ZoneId.systemDefault())
// val exactDate = dateFormatter.format(date)
// val exactTime = timeFormatter.format(date)
val exactDateTime = dateTimeFormatter.format(date)
val alarmDate = Date(friendReminderDate.toLong())
//Current date time
val dates = Date()
val stringFormat = SimpleDateFormat("dd-MM-yyyy hh:mm:ss a")
val dateTimeTo = stringFormat.format(dates.time)
//Set Alarm
if (alarmDate.after(dates)) {
Log.d("D", dates.toString())
Log.d("AlarmDate", alarmDate.toString())
Log.e("2 hour ago", dateTimeFormatter.format(date1))
println(friendReminderDate.toLong() - (120 * 60 * 1000))
Log.e("Set", exactDateTime)
val alarmManager: AlarmManager = context.getSystemService(
AppCompatActivity.ALARM_SERVICE) as AlarmManager
val alarmIntent = Intent(requireContext(), AlarmReceiver::class.java)
val pendingIntent = PendingIntent.getBroadcast(context, 0, alarmIntent, 0)
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) {
Log.e("Alarm", "Alarm")
alarmManager.setAlarmClock(AlarmManager.AlarmClockInfo(friendReminderDate.toLong() - 120*60*1000,
pendingIntent), pendingIntent)
} else {
Log.e("Alarm1", "${friendReminderDate.toLong() - (120 * 60 * 1000)}")
alarmManager.setExactAndAllowWhileIdle(AlarmManager.RTC_WAKEUP,
(friendReminderDate.toLong()) - 120 * 60 * 1000,
pendingIntent)
Log.e("Alarm2", "Alarm")
}
}
// if (exactDateTime > dateTimeTo) {
//
// }
}
}
if (friendReminderFromName != loggedInUser) {
if (friendReminderId != "") {
reminder = FriendsRemindersListModel(0, friendReminderId.toInt(), friendReminderText, friendReminderDate,
friendReminderFromName, friendReminderToName, friendReminderStatus)
}
}
if (getReminderListModel.size.toString() > remindersListModel.size.toString()) {
Log.e("serverListSize", getReminderListModel.size.toString())
Log.e("dbListSize", remindersListModel.size.toString())
Log.e("JsonListSize", jsonArray.length().toString())
for (i in 0 until getReminderListModel.size - 1) {
Log.e("present", getReminderListModel[i].reminderId.toString())
var isPresent = false
for (j in 0 until remindersListModel.size - 1) {
Log.e("present", remindersListModel.toString())
if (remindersListModel.isNotEmpty()) {
if (getReminderListModel[i].reminderId == remindersListModel[i].reminderId) {
isPresent = true
}
}
}
Log.e("presenting", "${!isPresent}")
if (isPresent) {
remindersViewModel.addingReminder(reminder)
}
}
}
else if (getReminderListModel.size.toString() < remindersListModel.size.toString()) {
for (i in 0 until remindersListModel.size - 1) {
for (j in 0 until getReminderListModel.size - 1) {
// var isRemoved = false
// Log.e("i's", i.toString())
Log.e("i's", getReminderListModel.size.toString())
Log.e("i'ss", remindersListModel.size.toString())
if (remindersListModel.isNotEmpty()) {
Log.e("delete3", remindersListModel[i].reminderId.toString())
Log.e("delete3", remindersListModel[i].reminderText)
Log.e("delete4", getReminderListModel[j].reminderId.toString())
Log.e("delete4", getReminderListModel[j].reminderText)
if (remindersListModel[i].reminderId != getReminderListModel[i].reminderId ) {
Log.e("delete2", remindersListModel[i].reminderId.toString())
remindersViewModel.deleteReminder(remindersListModel[i].reminderId)
// getReminderListAdapter.notifyItemRemoved(i)
}
}
}
}
}
// if (getReminderListModel.size.toString() != getRemindersDBList.size.toString()) {
// remindersViewModel.deleteReceivedReminders()
// remindersViewModel.addReminder(getReminderListModel)
// }
if (progressBar!= null) {
progressBar!!.visibility = View.GONE
}
}
}
getReminderHttpRequest.setOnErrorListener {
if (progressBar != null) {
progressBar!!.visibility = View.GONE
}
Log.e("getReminders error", "$it")
Log.e("Alarm1", "${friendReminderDate.toLong() - (120 * 60 * 1000)}")
}
val token = appGlobals.getValueString("userToken")
val headers = HttpHeaders("Authorization", "Token $token")
getReminderHttpRequest.get(AppGlobals.GET_REMINDERS_LIST_API, headers)
}
2. Alarm receiver class:
class AlarmReceiver: BroadcastReceiver() {
#RequiresApi(Build.VERSION_CODES.O)
#SuppressLint("UnsafeProtectedBroadcastReceiver")
override fun onReceive(context: Context?, intent: Intent?) {
showNotification(context!!, MessagingServiceFirebase.title, MessagingServiceFirebase.body)
Log.e("Checking notify", "Notification")
// Toast.makeText(context, "Alarm", Toast.LENGTH_SHORT).show()
Log.e("Checking ", "Notification")
// ringTone(context)
}
// private fun ringTone(context: Context) {
// val alert: Uri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_ALARM)
// val ringtone: Ringtone = RingtoneManager.getRingtone(context, alert)
//
// ringtone.play()
// Toast.makeText(context, "Alarm Called", Toast.LENGTH_SHORT).show()
// }
fun showNotification(ctx: Context, title: String, message: String) {
val notificationManager =
ctx.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
val channelId = "channel"
val name: CharSequence = "channel"
val description = "The channel"
val importance = NotificationManager.IMPORTANCE_HIGH
val mChannel = NotificationChannel(channelId, name, importance)
mChannel.description = description
mChannel.enableLights(true)
mChannel.lightColor = Color.RED
mChannel.enableVibration(true)
mChannel.vibrationPattern = longArrayOf(100, 200, 300, 400, 500, 400, 300, 200, 400)
mChannel.setShowBadge(false)
notificationManager.createNotificationChannel(mChannel)
}
val builder: NotificationCompat.Builder = NotificationCompat.Builder(ctx, "channel")
.setSmallIcon(R.drawable.ic_baseline_access_alarm_24)
.setContentTitle(title)
.setContentText(message)
val resultIntent = Intent(ctx, HomeActivity::class.java)
val stackBuilder: TaskStackBuilder = TaskStackBuilder.create(ctx)
stackBuilder.addParentStack(HomeActivity::class.java)
resultIntent.putExtra("NotifyTitle", title)
resultIntent.putExtra("NotifyMessage", message)
stackBuilder.addNextIntent(resultIntent)
val resultPendingIntent: PendingIntent = stackBuilder.getPendingIntent(0, PendingIntent.FLAG_UPDATE_CURRENT)
builder.setContentIntent(resultPendingIntent)
builder.setAutoCancel(true)
notificationManager.notify(12, builder.build())
}
}
3. Manifest code
<uses-permission android:name="android.permission.SCHEDULE_EXACT_ALARM" />
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>
<receiver
android:name=".AlarmReceiver"
android:enabled="true"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED" />
<action android:name="android.intent.action.LOCKED_BOOT_COMPLETED" />
</intent-filter>
</receiver>
You pull date from the JSON, and set an alarm for 2 hours before that? So if date is 6pm, you set an alarm for 4pm?
alarmManager.setExactAndAllowWhileIdle(
AlarmManager.RTC_WAKEUP,
friendReminderDate.toLong()) - 120 * 60 * 1000, // date - 2hrs
pendingIntent)
If it's 5pm right now, and you set an alarm for 4pm, it will still set, and fire immediately:
If the stated trigger time is in the past, the alarm will be triggered immediately. If there is already an alarm for this Intent scheduled (with the equality of two intents being defined by Intent#filterEquals), then it will be removed and replaced by this one.
So if you only want to set the alarm if now <= alarmTime, and just skip it if now > alarmTime, you need to do that check before you set the alarm.
It looks like you're trying to do that:
if (alarmDate.after(dates)) {
but alarmDate is "date", not "date - 2hrs" (you're using 6pm instead of 4pm):
val alarmDate = Date(friendReminderDate.toLong())
So during that 2-hour period, you're always setting alarms that fire immediately. You need to use your actual alarm time instead:
// seriously, just do this calculation once and refer to the variable
val alarmTime = friendReminderDate.toLong() - (120 * 60 * 1000)
val alarmDate = Date(alarmTime)
You have a lot of date variables piling up in there, it's confusing and hard to tell what's going on - that's probably how this alarmDate bug crept in.
Also just in case, you know your "alarm receiver" also fires and shows a notification when the device boots and when it first unlocks, right?
The (-2hrs) above is only correct, when you are in:
(UTC +1) zone AND there is SUMMER (+1) or
(UTC +2) zone AND there is WINTER (+0)
The correct datetime is in millis (kotlin datetime to millisecond convert using local zone and daylight offset):
val myalarmdatetime: String = "2022-05-31 23:59:59"
val myalarmdatetimemillis: Long =
ZonedDateTime.of(
LocalDateTime.parse(
myalarmdatetime,
DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")
), ZoneId.systemDefault()
).toInstant().toEpochMilli()

State flow Android Kotlin

I have a god view model for every thing I know this is wrong
but I am just experimenting with Flow
I have these two State flow variables in view model
private val _currentRestroMenu = MutableStateFlow<State<Menu>>(State.loading())
private val _userCart = MutableStateFlow(CustomerCart())
val currentRestroMenu: StateFlow<State<Menu>> = _currentRestroMenu
val userCart: StateFlow<CustomerCart> = _userCart
Below functions get data from server and update above state flow
private fun getRestroMenuFromCloudAndUpdateData(restroId: String) = viewModelScope.launch {
fireStoreRepository.getRestroMenu(restroId).collect { state ->
when (state) {
is State.Success -> {
_currentRestroMenu.value = State.success(state.data)
dataHolderMenuOnSearch = state.data
if (!viewedRestroMenu.contains(state.data)) {
viewedRestroMenu.add(state.data)
}
}
is State.Failed -> {
_currentRestroMenu.value = State.failed(state.message)
}
is State.Loading -> {
_currentRestroMenu.value = State.loading()
}
}
}
}
private fun getCart() = viewModelScope.launch(Dispatchers.IO) {
if (currentCart.cartEmpty) {
fireStoreRepository.getUserCartInfoFromCloud(dataStoreRepository.readFileDataStoreValue.first().savedUserId)
.collect { cartState ->
when (cartState) {
is State.Success -> {
_userCart.update {
it.copy(
cartId = cartState.data.cartId,
cartEmpty = cartState.data.cartEmpty,
cartItem = cartState.data.getCartItem(),
restroId = cartState.data.restroId,
cartTotalAmount = cartState.data.cartTotalAmount,
cartAddressId = cartState.data.cartAddressId,
cartDeliveryTime = cartState.data.cartDeliveryTime,
cartCookingInstructions = cartState.data.cartCookingInstructions,
cartAppliedOfferId = cartState.data.cartAppliedOfferId,
deliveryPartnerTipAmount = cartState.data.deliveryPartnerTipAmount,
cartDeliveryCharge = cartState.data.cartDeliveryCharge,
cartTax = cartState.data.cartTax,
deliveryInstructionId = cartState.data.deliveryInstructionId,
foodHandlingCharge = cartState.data.foodHandlingCharge,
cartNumberOfItems = cartState.data.cartNumberOfItems,
cartRestroName = cartState.data.cartRestroName
)
}
currentCart = cartState.data
}
is State.Failed -> {
if (cartState.message == "Result null") {
Log.d(
ContentValues.TAG,
"getCartFromCloud: No cart details found in cloud creating new cart"
)
_userCart.update {
it.copy(
cartId = dataStoreRepository.readFileDataStoreValue.first().savedUserId,
cartEmpty = true
)
}
currentCart = CustomerCart(
cartId = dataStoreRepository.readFileDataStoreValue.first().savedUserId,
cartEmpty = true
)
}
}
is State.Loading -> {
Log.d(ContentValues.TAG, "getCartFromCloud: Loading")
}
}
}
} else {
_userCart.value = currentCart
Log.d(ContentValues.TAG, "getCart: $currentCart ")
}
}
I am collecting these state flow from different fragments
every thing works fine except one fragment
here is the code
in on create method
viewLifecycleOwner.lifecycleScope.launch {
viewLifecycleOwner.lifecycle.repeatOnLifecycle(Lifecycle.State.STARTED) {
godCustomerViewModel.currentRestroMenu.collectLatest { menuState ->
Log.d(TAG, "currentRestroMenu ::: mENUSELECT FIRED: ")
when (menuState) {
is State.Success -> {
restroMenu = menuState.data
binding.recyclerView2.hideShimmer()
getCartDetails(restroMenu)
}
is State.Failed -> {
Log.d(TAG, "currentRestroMenu: ")
}
is State.Loading -> {
binding.recyclerView2.showShimmer()
}
}
}
}
}
private fun getCartDetails(restroMenu: Menu) = viewLifecycleOwner.lifecycleScope.launch {
viewLifecycleOwner.lifecycle.repeatOnLifecycle(Lifecycle.State.STARTED) {
godCustomerViewModel.userCart.collectLatest {
if (it.restroId == restroMenu.restroId) {
categoryAdapterRestroDetails.setData(
restroMenu.menuCategories,
it.getCartItem()
)
} else {
categoryAdapterRestroDetails.setData(
restroMenu.menuCategories,
ArrayList()
)
}
}
}
}
I am passing the two collected values to adapter (retro menu and item in cart )
when the fragment is loaded for the first time everything works fine
I have add dish to cart function which updates the value of user cart
fun addDishToCart(dish: Dish) = viewModelScope.launch {
Log.d(ContentValues.TAG, "addDishToCart: view model invoked")
if (currentCart.checkIfCartBelongsToThisRestro(dish.dishRestroId)) {
currentCart.addDishToCart(dish).collect {
Log.d(ContentValues.TAG, "addDishToCartcollect: $currentCart")
_userCart.update {
it.copy(
cartEmpty = currentCart.cartEmpty,
cartItem = currentCart.getCartItem(),
restroId = currentCart.restroId,
cartTotalAmount = currentCart.cartTotalAmount,
cartNumberOfItems = currentCart.cartNumberOfItems,
)
}
}
} else {
// restro Conflict
Log.d(ContentValues.TAG, "addDishToCart: $currentCart")
_restroConflict.value = CartConflict(true, currentCart.cartRestroName, dish)
}
Log.d(ContentValues.TAG, "addDishToCart current cart: ${currentCart.getCartItem()}")
Log.d(ContentValues.TAG, "addDishToCart: user Cart : ${_userCart.value.getCartItem()} ")
}
Which also work fine initially
I also have a button to filter menu to veg non veg
fun filterMenuForVeg(value: Boolean, showAll: Boolean) = viewModelScope.launch {
if (!showAll) {
Log.d(ContentValues.TAG, "filterMenuForVeg: Entered veg :$value")
var filteredMenu = Menu()
filteredMenu.restroId = dataHolderMenuOnSearch.restroId
for (menuCategory in dataHolderMenuOnSearch.menuCategories) {
Log.d(ContentValues.TAG, "filterMenuForVeg: $dataHolderMenuOnSearch ")
for (dish in menuCategory.dishes) {
if (dish.dishVeg == value) {
Log.d(ContentValues.TAG, "found dish with veg $value: ")
var categoryAlreadySaved = false
filteredMenu.menuCategories.filter {
categoryAlreadySaved = it.categoryId == menuCategory.categoryId
true
}
if (!categoryAlreadySaved) {
Log.d(ContentValues.TAG, "menu category not found in filtered list ")
val menuCategoryToAdd = MenuCategories()
menuCategoryToAdd.menuCategoryName = menuCategory.menuCategoryName
menuCategoryToAdd.categoryId = menuCategory.categoryId
menuCategoryToAdd.restroId = menuCategory.restroId
menuCategoryToAdd.dishes.add(dish)
filteredMenu.menuCategories.add(menuCategoryToAdd)
} else {
Log.d(ContentValues.TAG, "menu category found in filtered list ")
filteredMenu.menuCategories.find {
if (it.categoryId == menuCategory.categoryId) {
it.restroId = menuCategory.restroId
it.dishes.add(dish)
}
true
}
}
}
}
}
Log.d(ContentValues.TAG, "filterMenuForVeg : $filteredMenu ")
_currentRestroMenu.value = State.success(filteredMenu)
} else {
// set to all data
_currentRestroMenu.value = State.success(dataHolderMenuOnSearch)
}
When I filter dish for veg or non veg then add dish to cart (Which only changes userCart State flow) the place where I am collecting these state flow
get fired twice
so set data to adapter is getting called twice
What Iam doing wrong
Could you collect the items with onEach instead of collectLatest? It would solve your problem probably.