From 622bb221aba103a49ccc32c6aa7dcf6dd29a03a4 Mon Sep 17 00:00:00 2001 From: Sergio De la torre Date: Wed, 20 Nov 2024 08:03:45 +0100 Subject: [PATCH] feat: refs#6845 userInterface --- .../view/component/CustomDialogList.kt | 5 + .../fragment/CollectionCheckerViewModel.kt | 358 +++++ .../fragment/CollectionFragmentChecker.kt | 1198 +++++++++++++++++ 3 files changed, 1561 insertions(+) create mode 100644 app/src/main/java/es/verdnatura/presentation/view/feature/collection/fragment/CollectionCheckerViewModel.kt create mode 100644 app/src/main/java/es/verdnatura/presentation/view/feature/collection/fragment/CollectionFragmentChecker.kt diff --git a/app/src/main/java/es/verdnatura/presentation/view/component/CustomDialogList.kt b/app/src/main/java/es/verdnatura/presentation/view/component/CustomDialogList.kt index b97d1b1d..aaeaa032 100644 --- a/app/src/main/java/es/verdnatura/presentation/view/component/CustomDialogList.kt +++ b/app/src/main/java/es/verdnatura/presentation/view/component/CustomDialogList.kt @@ -130,6 +130,11 @@ class CustomDialogList(context: Context) : Dialog(context, R.style.DialogTheme) return this } + fun showDialog(): CustomDialogList { + binding.customDialogValue.visibility = View.VISIBLE + return this + } + fun hideDescription(): CustomDialogList { binding.customDialogDescription.visibility = View.GONE return this diff --git a/app/src/main/java/es/verdnatura/presentation/view/feature/collection/fragment/CollectionCheckerViewModel.kt b/app/src/main/java/es/verdnatura/presentation/view/feature/collection/fragment/CollectionCheckerViewModel.kt new file mode 100644 index 00000000..77ad2c28 --- /dev/null +++ b/app/src/main/java/es/verdnatura/presentation/view/feature/collection/fragment/CollectionCheckerViewModel.kt @@ -0,0 +1,358 @@ +package es.verdnatura.presentation.view.feature.collection.fragment + +import android.content.Context +import androidx.lifecycle.LiveData +import androidx.lifecycle.MutableLiveData +import androidx.lifecycle.map +import com.google.gson.JsonObject +import es.verdnatura.MobileApplication +import es.verdnatura.domain.SalixCallback +import es.verdnatura.domain.formatWithQuotes +import es.verdnatura.domain.toast +import es.verdnatura.domain.userCases.GetItemFromBarcodeUseCase +import es.verdnatura.presentation.base.BaseViewModel +import es.verdnatura.presentation.base.getMessageFromAllResponse +import es.verdnatura.presentation.base.nameofFunction +import es.verdnatura.presentation.common.Event +import es.verdnatura.presentation.common.PickupResponse +import es.verdnatura.presentation.common.SaleTrackingReplaceSalix +import es.verdnatura.presentation.common.TicketState +import es.verdnatura.presentation.view.feature.collection.SalixSaleQuantity +import es.verdnatura.presentation.view.feature.collection.mapper.map +import es.verdnatura.presentation.view.feature.sacador.model.CollectionVO +import es.verdnatura.presentation.view.feature.sacador.model.MistakeTypeListVO +import es.verdnatura.presentation.view.feature.sacador.model.MistakeTypeVO +import es.verdnatura.presentation.view.feature.workermistake.model.SaleMistakeSalix +import retrofit2.Response + +class CollectionCheckerViewModel(val context: Context) : BaseViewModel(context) { + private val getItemFromBarcodeUseCase = GetItemFromBarcodeUseCase(salix) + + //var isPaused: Boolean = false + + private val _isPaused = MutableLiveData() + val isPaused: LiveData get() = _isPaused + + private val _collectionTicketList by lazy { MutableLiveData() } + val collectionTicketList: LiveData = _collectionTicketList + val loadTicketList: LiveData> = _collectionTicketList.map { Event(it) } + + private val _responseSaleReplace by lazy { MutableLiveData() } + val responseSaleReplace: LiveData = _responseSaleReplace + val loadSaleReplace: LiveData> = _responseSaleReplace.map { Event(it) } + + private val _responseCollectionAddItem by lazy { MutableLiveData() } + val responseCollectionAddItem: LiveData = _responseCollectionAddItem + val loadResponseAddItem: LiveData> = _responseCollectionAddItem.map { Event(it) } + + private val _responsePrint by lazy { MutableLiveData() } + val responsePrint: LiveData = _responsePrint + val loadPrint: LiveData> = _responsePrint.map { Event(it) } + + private val _responseTicketState by lazy { MutableLiveData() } + val responseTicketState: LiveData = _responseTicketState + val loadTicketState: LiveData> = _responseTicketState.map { Event(it) } + + private val _responseTicketIsPickup by lazy { MutableLiveData() } + val responseTicketIsPickup: LiveData = _responseTicketIsPickup + val loadTicketIsPickup: LiveData> = _responseTicketIsPickup.map { Event(it) } + + private val _responseTicketClosure by lazy { MutableLiveData() } + val responseTicketClosure: LiveData = _responseTicketClosure + val loadTicketClousure: LiveData> = _responseTicketClosure.map { Event(it) } + + private val _responseCollectionUnchecked by lazy { MutableLiveData() } + val responseCollectionUnchecked: LiveData = _responseCollectionUnchecked + val loadCollectionUnchecked: LiveData> = + _responseCollectionUnchecked.map { Event(it) } + + private val _responseNew by lazy { MutableLiveData() } + val responseNew: LiveData = _responseNew + val loadAddNew: LiveData> = _responseNew.map { Event(it) } + + private val _responseIncQuantity by lazy { MutableLiveData() } + val responseIncQuantity: LiveData = _responseIncQuantity + val loadIncQuantity: LiveData> = _responseIncQuantity.map { Event(it) } + + private val _responseParking by lazy { MutableLiveData() } + val responseParking: LiveData = _responseParking + val loadParking: LiveData> = _responseParking.map { Event(it) } + + private val _mistakeList by lazy { MutableLiveData() } + val mistakeList: LiveData = _mistakeList + val loadMistakes: LiveData> = _mistakeList.map { Event(it) } + + fun getSales( + collectionFk: Number, print: String, source: String + + ) { + salix.getSalesFromTicketOrCollection( + collectionOrTicketFk = collectionFk, print = print != "0", source = source + ).enqueue(object : SalixCallback(context) { + override fun onError(t: Throwable) { + _collectionTicketList.value = CollectionVO( + 0, + isError = true, + errorMessage = getMessageFromAllResponse(nameofFunction(this), t.message!!) + ) + } + + override fun onSuccess(response: Response) { + try { + _collectionTicketList.value = response.body()?.let { it.map(context) } + } catch (ex: Exception) { + ex.toast(context) + } + + } + }) + } + + fun collectionGetId( + ticketFk: Int, print: String, type: String + ) { + salix.getCollectionId( + filter = """{"where":{"ticketFk":$ticketFk},"fields":"collectionFk"}""" + ).enqueue(object : SalixCallback>(context) { + override fun onError(t: Throwable) { + _collectionTicketList.value = CollectionVO( + 0, + isError = true, + errorMessage = getMessageFromAllResponse(nameofFunction(this), t.message!!) + ) + } + + override fun onSuccess(response: Response>) { + + if (response.body()!!.isNotEmpty()) { + + getSales( + response.body()!![0].entrySet().first().value.toString().toInt(), + print, + type + ) + + } else { + _collectionTicketList.value = CollectionVO( + 0, isError = false + ) + } + } + }) + } + + fun saleTrackingUpdate( + saleFk: Int, + originalQuantity: Int, + code: String, + isChecked: String, + buyFk: Long, + isScanned: Boolean? + ) { + salix.saleTrackingUpdate( + SaleTrackingReplaceSalix( + saleFk, originalQuantity, code, isChecked != "0", buyFk, isScanned!! + ) + ).enqueue(object : SalixCallback(context) { + override fun onSuccess(response: Response) { + _responseSaleReplace.value = true + } + + override fun onError(t: Throwable) { + _responseSaleReplace.value = false + super.onError(t) + } + }) + } + + fun collectionStickerPrint( + collectionFk: Int, labelCount: Int? + ) { + salix.collectionStickerPrint( + arrayListOf( + collectionFk, labelCount + ) + ).enqueue(object : SalixCallback(context) { + override fun onSuccess(response: Response) { + _responsePrint.value = true + } + + }) + } + + fun collectionAddItem( + itemFk: Int, quantity: Int, ticketFk: Int + ) { + + salix.addSale( + id = ticketFk, barcode = itemFk.toString(), quantity = quantity + ).enqueue(object : SalixCallback(context) { + override fun onError(t: Throwable) { + + _responseNew.value = false + } + + override fun onSuccess(response: Response) { + _responseNew.value = true + + } + }) + } + + fun setParking( + ticketFk: Int, parking: String + ) { + salix.setParking(arrayListOf(ticketFk, parking).formatWithQuotes()) + .enqueue(object : SalixCallback(context) { + override fun onSuccess(response: Response) { + _responseParking.value = true + super.onSuccess(response) + } + }) + } + + fun ticketStateTodaySetState( + ticketFk: Int, state: String + ) { + salix.ticketStateTodaySetState(arrayListOf(ticketFk, state).formatWithQuotes()) + .enqueue(object : SalixCallback(context) { + override fun onSuccess(response: Response) { + _responseTicketState.value = TicketState() + super.onSuccess(response) + } + }) + } + + fun collectionIncreaseQuantitySalix( + saleFk: Int, quantity: String + ) { + salix.collectionIncreaseQuantitySalix( + SalixSaleQuantity(saleId = saleFk, quantity = quantity.toInt()) + ).enqueue(object : SalixCallback(context) { + + override fun onSuccess(response: Response) { + super.onSuccess(response) + _responseIncQuantity.value = true + } + }) + } + + fun saleMistakeAdd( + saleFk: Int, typeFk: Int + ) { + salix.saleMistakeAdd( + SaleMistakeSalix( + userFk = (context as MobileApplication).userId!!, saleFk = saleFk, typeFk = typeFk + ) + ).enqueue(object : SalixCallback(context) { + + }) + } + + fun mistakeType() { + salix.getMistakeTypes().enqueue(object : SalixCallback>(context) { + override fun onSuccess(response: Response>) { + if (response.body() != null) { + _mistakeList.value = response.body()?.let { MistakeTypeListVO(it) } + } else { + val listError: ArrayList = ArrayList() + listError.add(MistakeTypeVO(0, "")) + _mistakeList.value = MistakeTypeListVO(listError) + } + } + + }) + } + + fun ticketIsOutClosureZone( + ticketFk: Int + ) { + salix.ticketIsOutClosureZone( + arrayListOf(ticketFk) + ).enqueue(object : SalixCallback(context) { + override fun onSuccess(response: Response) { + _responseTicketClosure.value = response.body()?.toString() ?: "false" + + } + + }) + } + + fun ticketState( + ticketFk: Int + ) { + salix.ticketState( + """{"where": {"ticketFk": "$ticketFk"},"include":[{"relation":"user","scope":{"fields":["username"]}}]}""" + + ).enqueue(object : SalixCallback>(context) { + override fun onSuccess(response: Response>) { + _responseTicketState.value = if (response.body()!!.isEmpty()) { + TicketState() + } else { + response.body()!![0] + } + } + + }) + } + + fun ticketIsPickup( + ticketFk: Number + ) { + salix.ticketIsPickup( + """{ + "where": { + "id": $ticketFk + }, + "fields": ["id", "routeFk"], + "include": [ + { + "relation": "route", + "scope": { + "fields": ["id", "agencyModeFk"], + "include": { + "relation": "agencyMode", + "scope": { + "fields": ["id", "deliveryMethodFk","code"], + "where": {"code": "REC_ALG"}, + "include": { + "relation": "deliveryMethod", + "scope": { + "fields": ["id", "code"] + } + } + } + } + } + } + ] + }""".trim() + + ).enqueue(object : SalixCallback>(context) { + override fun onSuccess(response: Response>) { + + _responseTicketIsPickup.value = + response.body() + ?.firstOrNull()?.route?.agencyMode?.deliveryMethod?.code == "PICKUP" + + } + + }) + } + + fun hasUncheckedTicket( + collectionFk: Int + ) { + salix.hasUncheckedTicket(collectionFk).enqueue(object : SalixCallback(context) { + override fun onSuccess(response: Response) { + _responseCollectionUnchecked.value = response.body()!!.toString() + + } + }) + } + + fun setPausedState(paused: Boolean) { + _isPaused.value = paused + } + +} \ No newline at end of file diff --git a/app/src/main/java/es/verdnatura/presentation/view/feature/collection/fragment/CollectionFragmentChecker.kt b/app/src/main/java/es/verdnatura/presentation/view/feature/collection/fragment/CollectionFragmentChecker.kt new file mode 100644 index 00000000..587e8b19 --- /dev/null +++ b/app/src/main/java/es/verdnatura/presentation/view/feature/collection/fragment/CollectionFragmentChecker.kt @@ -0,0 +1,1198 @@ +package es.verdnatura.presentation.view.feature.collection.fragment + +import android.content.Context +import android.graphics.drawable.Drawable +import android.media.MediaPlayer +import android.text.InputType.TYPE_CLASS_NUMBER +import android.view.KeyEvent +import android.view.KeyEvent.ACTION_DOWN +import android.view.View.GONE +import android.view.View.INVISIBLE +import android.view.View.VISIBLE +import android.view.WindowManager +import android.view.inputmethod.EditorInfo +import android.widget.ImageView +import android.widget.Toast +import androidx.recyclerview.widget.LinearLayoutManager +import com.google.gson.Gson +import es.verdnatura.R +import es.verdnatura.databinding.FragmentCollectionBinding +import es.verdnatura.domain.ConstAndValues +import es.verdnatura.domain.ConstAndValues.CONTROLADOR +import es.verdnatura.domain.ConstAndValues.PRINTERNAME +import es.verdnatura.domain.notNull +import es.verdnatura.domain.showToastCenterWithBackground +import es.verdnatura.domain.toast +import es.verdnatura.presentation.base.BaseFragment +import es.verdnatura.presentation.common.ItemScanned +import es.verdnatura.presentation.common.LabelDialogHelper +import es.verdnatura.presentation.common.OnBarcodeRowClickListener +import es.verdnatura.presentation.common.OnMistakeClickListener +import es.verdnatura.presentation.common.OnOptionsSelectedListener +import es.verdnatura.presentation.common.OnPackingClickListener +import es.verdnatura.presentation.common.OnPasillerosItemClickListener +import es.verdnatura.presentation.common.OnQuantityClickListener +import es.verdnatura.presentation.common.OnSaleClickListener +import es.verdnatura.presentation.common.OnTicketClickListener +import es.verdnatura.presentation.common.OnTicketColorListener +import es.verdnatura.presentation.common.ToolBarAdapterTooltip +import es.verdnatura.presentation.common.hideKeyboard +import es.verdnatura.presentation.common.itemScanIsQr +import es.verdnatura.presentation.common.itemScanValue +import es.verdnatura.presentation.view.component.CustomDialog +import es.verdnatura.presentation.view.component.CustomDialogInput +import es.verdnatura.presentation.view.component.CustomDialogList +import es.verdnatura.presentation.view.component.CustomDialogThreeButtons +import es.verdnatura.presentation.view.feature.articulo.adapter.BarcodeAdapter +import es.verdnatura.presentation.view.feature.articulo.model.BarcodeVO +import es.verdnatura.presentation.view.feature.collection.adapter.SaleAdapter +import es.verdnatura.presentation.view.feature.main.activity.MainActivity +import es.verdnatura.presentation.view.feature.pasillero.model.PasillerosItemVO +import es.verdnatura.presentation.view.feature.sacador.model.CollectionVO +import es.verdnatura.presentation.view.feature.sacador.model.MistakeTypeVO +import es.verdnatura.presentation.view.feature.sacador.model.PlacementVO +import es.verdnatura.presentation.view.feature.sacador.model.SaleVO +import org.json.JSONObject + +// FALTA TESTEAR REVISORES DESPUÉS DE CAMPAÑA Y VER HOLDPOSITION +@Suppress("UNUSED_ANONYMOUS_PARAMETER") +class CollectionFragmentChecker( + var collection: CollectionVO = CollectionVO(0), var type: String = CONTROLADOR +) : BaseFragment(CollectionCheckerViewModel::class) { + + private var sales: List = listOf() + private var salesParent: List = listOf() + private var saleAdapter: SaleAdapter? = null + private var lm: LinearLayoutManager? = null + private var pasillerosItemClickListener: OnPasillerosItemClickListener? = null + private lateinit var customDialogList: CustomDialogList + private var placementSupplyAdapter: BarcodeAdapter? = null + private var listPlacementSupply: ArrayList = ArrayList() + private var storedShelvingPosition: Int = 0 + private lateinit var customDialogInput: CustomDialogInput + private lateinit var customDialogThreeButtons: CustomDialogThreeButtons + private var ticketSelected: Int = 0 + private lateinit var customDialog: CustomDialog + var mperror: MediaPlayer? = null + var mpok: MediaPlayer? = null + private var tickets: ArrayList = ArrayList() + private var mistakeSale: SaleVO? = null + private var positionIncreaseQuantity = 0 + private var quantityIncrease: Int = 0 + private var isMarking = false + private lateinit var ticketScanTxt: String + private var lastScanned: Int = 0 + private var buttonPushedGetCollection = false + private var isScanned: Boolean? = null + private var canChangeState = true + private var allTicketsChecked = false + private var myPosition = 0 + private var isMarkedSalePrevious = false + private var inPause = false + private var hasFilterByLevel = false + private lateinit var myGroupList: List + + companion object { + fun newInstance(collection: CollectionVO, type: String) = + CollectionFragmentChecker(collection, type) + } + + override fun onAttach(context: Context) { + if (context is OnPasillerosItemClickListener) pasillerosItemClickListener = context + super.onAttach(context) + } + + override fun getLayoutId(): Int = R.layout.fragment_collection + + override fun onResume() { + super.onResume() + scanRequest() + } + + override fun init() { + mperror = MediaPlayer.create((activity as MainActivity), R.raw.error) + mpok = MediaPlayer.create((activity as MainActivity), R.raw.ok) + customDialogList = CustomDialogList(requireContext()) + customDialogInput = CustomDialogInput(requireContext()) + customDialog = CustomDialog(requireContext()) + customDialogThreeButtons = CustomDialogThreeButtons(requireContext()) + ma.hideBottomNavigation(GONE) + setEvents() + setToolBar() + if (collection.tickets.isNotEmpty()) { + createCollectionList() + } + super.init() + } + + override fun onPause() { + super.onPause() + //viewModel.isPaused = true + viewModel.setPausedState(true) + + } + + private fun setToolBar() { + binding.mainToolbar.toolbarSubtitle.visibility = VISIBLE + binding.mainToolbar.toolbarIcons.visibility = VISIBLE + binding.mainToolbar.backButton.visibility = VISIBLE + binding.previaButton.visibility = INVISIBLE + binding.mainToolbar.toolbarTitle.text = + if (collection.collectionFk == 0) getString(R.string.review) else collection.collectionFk.toString() + + val listIcons: ArrayList = ArrayList() + val iconPrint = ImageView(context) + iconPrint.setImageResource(R.drawable.ic_print_black_24dp) + val iconAdd = ImageView(context) + iconAdd.setImageResource(R.drawable.ic_playlist_add_black_24dp) + val iconViewCollection = ImageView(context) + iconViewCollection.setImageResource(R.drawable.ic_collection) + val iconWorker = ImageView(context) + iconWorker.setImageResource(R.drawable.ic_worker) + val iconParking = ImageView(context) + iconParking.setImageResource(R.drawable.ic_local_parking_black_24dp) + val iconUpdate = ImageView(context) + iconUpdate.setImageResource(R.drawable.ic_autorenew_black_24dp) + + iconPrint.tooltipText = getTooltip(R.drawable.ic_print_black_24dp) + iconAdd.tooltipText = getTooltip(R.drawable.ic_playlist_add_black_24dp) + iconViewCollection.tooltipText = getTooltip(R.drawable.ic_collection) + iconParking.tooltipText = getTooltip(R.drawable.ic_local_parking_black_24dp) + iconUpdate.tooltipText = getTooltip(R.drawable.ic_autorenew_black_24dp) + + listIcons.add(iconPrint) + listIcons.add(iconViewCollection) + listIcons.add(iconWorker) + listIcons.add(iconAdd) + binding.previaButton.setOnClickListener { + showPrevia() + } + + + binding.mainToolbar.toolbarIcons.adapter = + ToolBarAdapterTooltip(listIcons, object : OnOptionsSelectedListener { + override fun onOptionsItemSelected(item: Drawable) { + if (collection.tickets.isNotEmpty()) + when (item) { + iconViewCollection.drawable -> getCollection() + iconPrint.drawable -> print() + iconAdd.drawable -> addItem() + iconWorker.drawable -> showUser() + iconUpdate.drawable -> updateScreen() + iconParking.drawable -> pasillerosItemClickListener?.onPasillerosItemClickListener( + PasillerosItemVO( + title = R.string.Parking + ), "" + ) + } + + } + }) + binding.mainToolbar.toolbarIcons.layoutManager = + LinearLayoutManager(requireContext(), LinearLayoutManager.HORIZONTAL, false) + } + + private fun updateScreen() { + canChangeState = false + viewModel.getSales( + collection.collectionFk, print = "0", type + ) + } + + private fun markPrevia(saleGroupScanned: String) { + for (indice in sales.indices) { + if (!sales[indice].saleGroupFk.isNullOrEmpty() && sales[indice].saleGroupFk == saleGroupScanned) { + markLine(indice) + mpok!!.start() + + } + } + } + + private fun showPrevia() { + customDialogList.getEditText().setRawInputType(TYPE_CLASS_NUMBER) + customDialogList.setTitle(getString(R.string.scanPreviousTicket)) + .setOkButton(getString(R.string.end)) { + takeActionPrevia(customDialogList) + + }.setValue("").show() + + customDialogList.getEditText().requestFocus() + ma.hideKeyboard(customDialogList.getEditText()) + + customDialogList.getEditText().setOnEditorActionListener { v, actionId, event -> + if (actionId == EditorInfo.IME_ACTION_SEARCH || actionId == EditorInfo.IME_ACTION_DONE || actionId == 0 || actionId == 5) { + if (customDialogList.getValue().isNotEmpty()) { + isScanned = + event != null && event.action == ACTION_DOWN && event.keyCode == KeyEvent.KEYCODE_ENTER + takeActionPrevia(customDialogList) + } + customDialogList.setValue("") + ma.hideKeyboard(customDialogList.getEditText()) + return@setOnEditorActionListener true + } + false + } + hideKeyboard() + } + + private fun takeActionPrevia(customDialogList: CustomDialogList) { + println("previaaaa ${customDialogList.getValue()}") + + ma.hideKeyboard(customDialogList.getEditText()) + try { + val saleGroupScanned = itemScanValue( + customDialogList.getValue(), arrayOf("saleGroup"), "id" + ).toString() + + markPrevia(saleGroupScanned) + customDialogList.dismiss() + } catch (ex: Exception) { + ma.messageWithSound( + message = ex.message.toString(), isError = true, isPlayed = true, isToasted = true + ) + } + } + + private fun getCollection() { + + buttonPushedGetCollection = if (!buttonPushedGetCollection) { + viewModel.collectionGetId( + collection.collectionFk, print = "0", type + ) + true + } else { + viewModel.getSales( + lastScanned, print = "0", type + + ) + false + } + lastScanned = collection.collectionFk + } + + private fun scanRequest() { + binding.scanInput.requestFocus() + requireActivity().hideKeyboard() + } + + private fun showUser() { + + ma.onPasillerosItemClickListener( + PasillerosItemVO(title = R.string.titleUserControlVehicle), + collection.tickets[0].sales[0].workerFk + ) + + } + + private fun setEvents() { + + binding.mainToolbar.backButton.setOnClickListener { + ma.onMyBackPressed() + } + requireActivity().hideKeyboard() + binding.scanInput.requestFocus() + binding.scanInput.setOnEditorActionListener { v, actionId, event -> + if (actionId == EditorInfo.IME_ACTION_SEARCH || actionId == EditorInfo.IME_ACTION_DONE || actionId == 0 || actionId == 5) {//ID=0 ACTION_NEXT ID=5 ACTION_UNESPECEFIED) + if (binding.scanInput.text.toString().isNotEmpty()) { + + //sergio:para ver si ha marcado dos veces el mismo ticket + binding.scanInput.setText(textScannedFilterDouble(binding.scanInput.text!!.toString())) + isScanned = + event != null && event.action == ACTION_DOWN && event.keyCode == KeyEvent.KEYCODE_ENTER + + if (itemScanIsQr(binding.scanInput.text.toString())) { + + val myQr = ItemScanned(JSONObject(binding.scanInput.text.toString())) + + when (myQr.table) { + "saleGroup" -> { + markPrevia(myQr.id.toString()) + } + + "buy" -> binding.scanInput.setText(myQr.more) + "ticket" -> findSale(myQr.id.toString()) + } + + } else { + if (sales.any { it.saleGroupFk == binding.scanInput.text.toString() }) { + markPrevia(binding.scanInput.text.toString()) + } else { + findSale(binding.scanInput.text.toString()) + } + + } + + buttonPushedGetCollection = false + + } + binding.scanInput.setText("") + requireActivity().hideKeyboard() + return@setOnEditorActionListener true + } + true + } + requireActivity().hideKeyboard() + //No se pone source en la llamada para que no cambie el estado + binding.collectionSwipe.setOnRefreshListener { + canChangeState = false + isMarking = false + binding.collectionSwipe.isRefreshing = false + viewModel.getSales( + collection.collectionFk, print = "0", " " + ) + buttonPushedGetCollection = false + binding.collectionSwipe.isRefreshing = false + } + } + + override fun observeViewModel() { + with(viewModel) { + + loadTicketList.observe(viewLifecycleOwner) { event -> + event.getContentIfNotHandled().notNull { + + if (!it.isError) { + if (it.tickets.isNotEmpty()) { + collection = it + binding.previaButton.visibility = VISIBLE + binding.fragmentSacadorCollections.visibility = VISIBLE + createCollectionList() + } else { + + binding.mainToolbar.toolbarSubtitle.text = + getString(R.string.summaryCount, 0, 0) + binding.fragmentSacadorCollections.visibility = INVISIBLE + binding.previaButton.visibility = INVISIBLE + } + } else { + customDialog.setTitle(getString(R.string.error)) + .setDescription(it.errorMessage) + .setOkButton(getString(R.string.accept)) { + customDialog.dismiss() + if (activity != null) ma.onMyBackPressed() + }.show() + } + + } + } + loadTicketIsPickup.observe(viewLifecycleOwner) { event -> + event.getContentIfNotHandled().notNull { + if (it) { + val customDialogWarning = CustomDialog(requireContext()) + customDialogWarning.setTitle(getString(R.string.ticketPickup)) + customDialogWarning.setDescription( + getString( + R.string.ticketPickupDescr, + binding.mainToolbar.toolbarTitle.text + ) + ) + .setOkButton(getString(R.string.aware)) { + customDialogWarning.dismiss() + } + customDialogWarning.show() + + } + } + } + loadParking.observe(viewLifecycleOwner) { event -> + event.getContentIfNotHandled().notNull { + context.showToastCenterWithBackground( + getString( + R.string.parkingIn, + ticketScanTxt + ) + ) + } + } + + loadPrint.observe(viewLifecycleOwner) { event -> + event.getContentIfNotHandled().notNull { + (getString(R.string.Imprimiendo) + mobileApplication.dataStoreApp.readDataStoreKey( + PRINTERNAME + )).toast( + requireContext() + ) + } + + } + + loadAddNew.observe(viewLifecycleOwner) { event -> + event.getContentIfNotHandled().notNull { + if (!it) { + customDialog.setTitle(getString(R.string.disponibility)) + .setDescription(getString(R.string.errorCollectionNew)) + .setKoButton(getString(R.string.close)) { + scanRequest() + customDialog.dismiss() + }.show() + } else { + viewModel.getSales( + collection.collectionFk, print = "0", type + ) + + } + + } + } + + loadTicketState.observe(viewLifecycleOwner) { event -> + event.getContentIfNotHandled().notNull { + if ((it.code == "ON_CHECKING" || it.code == "CHECKED") && it.user.id != mobileApplication.userId) { + val customDialogWarningChecking = CustomDialog(requireContext()) + customDialogWarningChecking.setTitle(getString(R.string.info)) + customDialogWarningChecking.setDescription( + if (it.code == "ON_CHECKING") { + getString(R.string.checkingByUser, it.user.username) + } else { + getString(R.string.checkedByUser, it.user.username) + } + ).setOkButton(getString(R.string.aware)) { + customDialogWarningChecking.dismiss() + }.show() + } + } + } + + loadTicketClousure.observe(viewLifecycleOwner) { event -> + event.getContentIfNotHandled().notNull { + if (it.toBoolean()) { + val customDialogWarning = CustomDialog(requireContext()) + customDialogWarning.setTitle(getString(R.string.urgentWarning)) + customDialogWarning.setDescription(getString(R.string.ticketWarning)) + .setOkButton(getString(R.string.aware)) { + customDialogWarning.dismiss() + }.show() + } + } + } + + loadIncQuantity.observe(viewLifecycleOwner) { event -> + event.getContentIfNotHandled().notNull { + incresaseSuccesful() + } + } + + //sergio: para si hay algun ticket por revisar antes de parkinear + + loadCollectionUnchecked.observe(viewLifecycleOwner) { event -> + event.getContentIfNotHandled().notNull { + + //sergio: devuelve false si no hay para revisar y <> false. + if (it != "false") { + customDialog.setTitle(getString(R.string.warning)) + .setDescription(getString(R.string.pendingReviewParking) + (it)) + .setOkButton(getString(R.string.accept)) { + customDialog.dismiss() + + }.setKoButton(getString(R.string.review)) { + viewModel.getSales( + it.toInt(), print = "0", type + ) + customDialog.dismiss() + } + customDialog.show() + } else { + viewModel.setParking( + ticketFk = tickets[0].toInt(), parking = ticketScanTxt + ) + } + + } + } + + loadSaleReplace.observe(viewLifecycleOwner) { event -> + event.getContentIfNotHandled().notNull { + if (!it) { + viewModel.getSales( + collection.collectionFk, print = "0", type + ) + + } else { + checkStateParent() + setTotalLines() + setListPosition() + } + } + } + + loadMistakes.observe(viewLifecycleOwner) { event -> + event.getContentIfNotHandled().notNull { + showMistakeList(it.list) + } + } + + isPaused.observe(viewLifecycleOwner) { + inPause = it + } + + } + } + + //CREATE LIST + private fun createCollectionList() { + val salesList: ArrayList = ArrayList() + tickets = ArrayList() + var observations = "" + collection.tickets.forEach { ticket -> + ticket.sales.forEach { saleVO -> + salesList.add(saleVO) + if (tickets.firstOrNull { it == saleVO.ticketFk }.isNullOrEmpty()) tickets.add( + saleVO.ticketFk + ) + } + + observations = + observations.takeIf { it.isNotBlank() }?.plus(" ${ticket.observations}") ?: "" + } + + if (!buttonPushedGetCollection) { + sales = salesList.sortedWith(compareBy { it.picked }) + myGroupList = groupSaleGroup(salesList).sortedWith(compareBy { it.picked }) + } else { + sales = salesList.sortedWith( + compareBy({ it.isControlled }, { it.picked }) + ) + myGroupList = groupSaleGroup(salesList).sortedWith( + compareBy({ it.isControlled }, { it.picked }) + ) + } + + /*sales = salesList.sortedWith( + compareBy({ it.isControlled }, { it.picked }) + )*/ + + /* myGroupList = groupSaleGroup(salesList).sortedWith( + compareBy({ it.isControlled }, { it.picked }) + )*/ + + saleAdapter = SaleAdapter( + myGroupList as MutableList, + pasillerosItemClickListener!!, + object : OnQuantityClickListener { + override fun onQuantityClick(sale: SaleVO) { + + myGroupList.forEachIndexed { index, saleVO -> + if (saleVO.saleFk == sale.saleFk) { + showQuantityDialog(index) + } + } + + } + }, + object : OnSaleClickListener { + override fun onSaleClick(sale: SaleVO) { + + sales.forEachIndexed { index, saleVO -> + if (saleVO.saleFk == sale.saleFk) { + isScanned = false + markLine(index) + } + + } + } + + }, + object : OnMistakeClickListener { + override fun onMistakeClickListener(sale: SaleVO) { + + viewModel.mistakeType() + mistakeSale = sale + + } + }, + object : OnPackingClickListener { + override fun onPackingClick(sale: SaleVO) { + } + }, + object : OnTicketClickListener { + override fun onTicketClickListener(sale: SaleVO) { + + val entryPoint = Gson().toJson( + mutableMapOf( + "entryPoint" to sale.ticketFk, "web" to "${ + mobileApplication.dataStoreApp.getServerSalix() + }/#!/ticket/${sale.ticketFk}/sale" + ) + ) + ma.onPasillerosItemClickListener( + PasillerosItemVO( + title = R.string.titleWebViewer, + ), entryPoint = entryPoint + ) + + } + }, + type = type, + onTicketColorClickListener = object : OnTicketColorListener { + override fun onTicketColorListener(sale: SaleVO) { + hasFilterByLevel = !hasFilterByLevel + + if (hasFilterByLevel) { + if (buttonPushedGetCollection) { + saleAdapter!!.updateSales(myGroupList.filter { it.level == sale.level } as MutableList) + myGroupList = myGroupList.filter { it.level == sale.level } + } + } else { + createCollectionList() + } + + } + } + ) + + lm = LinearLayoutManager(requireContext(), LinearLayoutManager.VERTICAL, false) + binding.fragmentSacadorCollections.adapter = saleAdapter + binding.fragmentSacadorCollections.layoutManager = lm + setTotalLines() + printObservations(observations) + saleAdapter!!.notifyDataSetChanged() + } + + private fun printObservations(observations: String) { + if (observations.trim().isNotEmpty()) { + customDialog.setTitle(getString(R.string.observations)).setDescription(observations) + .setOkButton(getString(R.string.accept)) { + customDialog.hide() + customDialog.dismiss() + }.show() + } + } + + private fun findSale(txtscan: String) { + var index = 0 + var isBreak = false + var isOk = false + + + try { + for (saleVO in sales) { // sales no tiene parent + + if (saleVO.isControlled == "0") { + + if (txtscan == saleVO.itemFk.toString()) { + if (mpok != null) mpok!!.start() + isOk = true + markLine(index) + break + } + //2- Por barcode + saleVO.barcodes.forEach { barcode -> + + if (txtscan == barcode) { + if (mpok != null) mpok!!.start() + isOk = true + markLine(index) + isBreak = true + } + } + + if (isBreak) break + } + index += 1 + } + } catch (ex: Exception) { + getString(R.string.errorInput).toast(requireContext()) + } + if (!isOk) { + if (txtscan.contains("-")) { + + if (tickets.size > 0) { + + ticketScanTxt = txtscan + viewModel.hasUncheckedTicket( + collectionFk = tickets[0].toInt() + ) + } + + } else { + + isMarking = false + try { + val myScan = txtscan.toInt() + val hasItemSales = sales.any { + it.itemFk == txtscan.toInt() + } + if (!hasItemSales) { + binding.mainToolbar.toolbarTitle.text = txtscan + viewModel.getSales( + myScan, print = "0", "ON_CHECKING" + ) + viewModel.ticketIsOutClosureZone( + myScan + ) + viewModel.ticketState(myScan) + viewModel.ticketIsPickup(myScan) + + } else { + mperror!!.start() + } + + } catch (ex: Exception) { + + getString(R.string.errorInput).toast(requireContext()) + } + + } + } + } + + private fun markLine(position: Int) { + + //Falta averiguar la saleFk donde está y modificar si es la hija. + //Busco al padre y ya está y esa es la posición , se puede cambiar antes porque si falla haré un getSales + + val isParentPrevia = + myGroupList.any { it.saleGroupFk == sales[position].saleGroupFk && it.isParent } + + if (sales[position].saleGroupFk == null || sales[position].saleGroupFk == "" || !isParentPrevia) { + myPosition = myGroupList.indexOfFirst { it.saleFk == sales[position].saleFk } + myGroupList[myPosition].isControlled = + if (myGroupList[myPosition].isControlled == "1") "0" else "1" + isMarkedSalePrevious = false + } else { + //buscar padre y marcar position + val myPositionParent = + myGroupList.indexOfFirst { it.saleGroupFk == sales[position].saleGroupFk && it.isParent } + myPosition = myPositionParent + val myList = myGroupList[myPositionParent].sonSales + val myPositionSon = myList.indexOfFirst { it.saleFk == sales[position].saleFk } + + myGroupList[myPositionParent].sonSales[myPositionSon].isControlled = + if (myGroupList[myPositionParent].sonSales[myPositionSon].isControlled == "1") "0" else "1" + isMarkedSalePrevious = true + + } + viewModel.saleTrackingUpdate( + saleFk = sales[position].saleFk, + isChecked = sales[position].isControlled, + originalQuantity = sales[position].pickedQuantity!!, + code = "CHECKED", + buyFk = 0, + isScanned = isScanned + + ) + checkStateParent() + saleAdapter!!.notifyItemChanged(myPosition) + canChangeState = true + isMarking = true + } + + private fun checkStateParent() { + for (s in myGroupList) { + if (s.isParent) { + val totalLines = s.sonSales.size + val isPreviousPrepared = s.sonSales.filter { it.isPreviousPrepared == "1" }.size + val isPrepared = s.sonSales.filter { it.isPrepared == "1" }.size + val isControlled = s.sonSales.filter { it.isControlled == "1" }.size + val isPreControlled = s.sonSales.filter { it.isPreControlled == "1" }.size + if (totalLines == isPreviousPrepared) { + s.isPreviousPrepared = "1" + } else { + s.isPreviousPrepared = "0" + } + if (totalLines == isPrepared) { + s.isPrepared = "1" + } else { + s.isPrepared = "0" + } + if (totalLines == isControlled) { + s.isControlled = "1" + } else { + s.isControlled = "0" + } + if (totalLines == isPreControlled) { + s.isPreControlled = "1" + } else { + s.isPreControlled = "0" + } + + } + } + + } + + private fun setListPosition() { + + if (inPause) { + //viewModel.isPaused = false + viewModel.setPausedState(false) + } else { + if (mobileApplication.dataStoreApp.readDataStoreKey( + ConstAndValues.HOLDPOSITION + ) + ) { + if (!myGroupList[myPosition].isParent) { // si no es previa movemos + + /* lm!!.scrollToPositionWithOffset(myPosition, 0) + } else {*/ + lm!!.scrollToPositionWithOffset( + if (myGroupList[myPosition].isControlled == "1") myPosition + 1 else myPosition, + 0 + ) + //} + + } else { + lm!!.scrollToPositionWithOffset(myPosition, 0) + } + } + } + } + + private fun reviewQuantityForRefreshingAndSorting( + quantityTotal: Int, quantityPicked: Int + ) { + + if (quantityPicked < quantityTotal) { + + viewModel.getSales( + collection.collectionFk, print = "0", "ON_CHECKING" + ) + + } else { + setListPosition() + } + + } + + private fun print() { + + if (ma.havePrinter() && ma.haveSector()) { + showDialogLabelCount() + + } else { + + ma.messageWithSound( + getString(R.string.printerFault), + isError = true, + true, + getString(R.string.printError), + false + ) + + } + + } + + private fun addItem() { + listPlacementSupply = ArrayList() + collection.tickets.forEach { + listPlacementSupply.add(BarcodeVO(code = it.ticketFk)) + } + if (listPlacementSupply.size == 1) { + ticketSelected = listPlacementSupply[0].code!!.toInt() + } + customDialogList.window?.setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_VISIBLE) + customDialogList.getEditTextTwo().inputType = TYPE_CLASS_NUMBER + customDialogList.getEditText().setRawInputType(TYPE_CLASS_NUMBER) + customDialogList.setTitle(getString(R.string.Agregarartículoparaticket) + " " + ticketSelected) + .setOkButton(getString(R.string.Agregar)) { + + if (ticketSelected == 0) { + getString(R.string.Seleccionaunticketdelaista).toast(requireContext()) + } else if (customDialogList.getValue().isEmpty() || customDialogList.getValueTwo() + .isEmpty() + ) { + getString(R.string.Todosloscampossonobligatorios).toast(requireContext()) + } else { + + viewModel.collectionAddItem( + itemFk = customDialogList.getValue().toInt(), + ticketFk = ticketSelected, + quantity = customDialogList.getValueTwo().toInt() + ) + + + scanRequest() + customDialogList.dismiss() + } + + }.setKoButton(getString(R.string.close)) { + scanRequest() + customDialogList.dismiss() + }.setHintValue(getString(R.string.Artículo)).setValue("") + .setHintValueTwo(getString(R.string.Cantidad)).setValueTwo("").show() + customDialogList.getEditText().requestFocus() + requireActivity().hideKeyboard() + + customDialogList.getEditText().setOnEditorActionListener { v, actionId, event -> + if (actionId == EditorInfo.IME_ACTION_SEARCH || actionId == EditorInfo.IME_ACTION_DONE || actionId == 0 || actionId == 5) { + if (customDialogList.getValue().isNotEmpty()) { + try { + customDialogList.setValue( + itemScanValue( + customDialogList.getValue(), arrayOf("buy"), "more" + ).toString() + ) + + } catch (e: Exception) { + ma.messageWithSound(e.message.toString(), isError = true, isPlayed = true) + } + customDialogList.getEditTextTwo().requestFocus() + } + //requireActivity().hideKeyboard() + return@setOnEditorActionListener true + + } + false + + } + + + customDialogList.getEditTextTwo().setOnEditorActionListener { v, actionId, event -> + if (actionId == EditorInfo.IME_ACTION_SEARCH || actionId == EditorInfo.IME_ACTION_DONE || actionId == 0 || actionId == 5) { + if (customDialogList.getValueTwo().isNotEmpty()) { + if (ticketSelected == 0) { + getString(R.string.Seleccionaunticketdelaista).toast(requireContext()) + } else if (customDialogList.getValue() + .isEmpty() || customDialogList.getValueTwo().isEmpty() + ) { + getString(R.string.Todosloscampossonobligatorios).toast(requireContext()) + } else { + + viewModel.collectionAddItem( + itemFk = customDialogList.getValue().toInt(), + ticketFk = ticketSelected, + quantity = customDialogList.getValueTwo().toInt(), + ) + scanRequest() + customDialogList.dismiss() + } + } + requireActivity().hideKeyboard() + return@setOnEditorActionListener true + } + false + } + + placementSupplyAdapter = + BarcodeAdapter(listPlacementSupply, object : OnBarcodeRowClickListener { + override fun onBarcodeRowClickListener(item: BarcodeVO) { + customDialogInput.setTitle(getString(R.string.ArtículoparaTicket) + " " + item.code!!) + ticketSelected = item.code!!.toInt() + customDialogList.setTitle(getString(R.string.Agregarartículoparaticket) + " " + ticketSelected) + } + }, showDelete = false) + + customDialogList.getRecyclerView().adapter = placementSupplyAdapter + + customDialogList.getRecyclerView().layoutManager = + LinearLayoutManager(requireContext(), LinearLayoutManager.VERTICAL, false) + + } + + private fun setTotalLines() { + + val totalMark = sales.count { (it.isControlled == "1") && !it.isParent } + binding.mainToolbar.toolbarTitle.text = + collection.collectionFk.takeIf { it != 0 }?.toString() ?: "" + binding.mainToolbar.toolbarSubtitle.text = + getString(R.string.summaryCount, totalMark, sales.size) + + if (totalMark == sales.size) { + getString(R.string.completCollection).toast(this.context, Toast.LENGTH_SHORT) + // saleAdapter!!.notifyDataSetChanged() + + if (canChangeState) changeTicketState() + } else { + if (allTicketsChecked) { + + sales.forEach { + if (it.isControlled == "0") { + viewModel.ticketStateTodaySetState( + ticketFk = it.ticketFk.toInt(), state = "ON_CHECKING" + ) + } + } + allTicketsChecked = false + } + } + } + + private fun showQuantityDialog(position: Int) { + try { + + customDialogThreeButtons.setDescription(getString(R.string.itemSaleQuantity)) + .setValue("").setOkButtonAdd(getString(R.string.modify)) { + try { + increaseQuantity(position, customDialogThreeButtons.getValue().toInt()) + scanRequest() + customDialogThreeButtons.dismiss() + } catch (ex: Exception) { + ma.messageWithSound( + message = getString(R.string.errorInputQuantity), + isPlayed = true, + isError = true, + isToasted = true + ) + } + + }.setKoButton(getString(R.string.cancel)) { + scanRequest() + customDialogThreeButtons.dismiss() + }.show() + customDialogThreeButtons.setFocusDialogValue() + } catch (ex: Exception) { + getString(R.string.errorInput).toast(requireContext()) + } + } + + private fun incresaseSuccesful() { + try { + sales[positionIncreaseQuantity].quantity = quantityIncrease + + } catch (e: Exception) { + e.message!!.toast(requireContext()) + } + saleAdapter?.notifyDataSetChanged() + sales[positionIncreaseQuantity].originalQuantity = quantityIncrease + } + + private fun increaseQuantity(position: Int, quantity: Int) { + positionIncreaseQuantity = position + quantityIncrease = quantity + viewModel.collectionIncreaseQuantitySalix( + saleFk = sales[position].saleFk, quantity = quantity.toString() + ) + + } + + private fun changeTicketState() { + if (!inPause) tickets.forEach { + viewModel.ticketStateTodaySetState( + ticketFk = it.toInt(), state = "CHECKED" + ) + } + allTicketsChecked = true + + } + + private fun showErrorMessage(text: String) { + customDialog.setTitle(getString(R.string.errorMarkLine)).setDescription(text) + .setKoButton(getString(R.string.close)) { + customDialog.dismiss() + }.show() + } + + private fun showDialogLabelCount() { + var isTicket = false + for (t in collection.tickets) { + if (t.ticketFk.toInt() == (collection.collectionFk)) { + isTicket = true + } + } + if (isTicket) { + val labelDialogHelper = LabelDialogHelper(requireContext()) + labelDialogHelper.showLabelDialog( + onItemSelected = { labelCount -> + viewModel.collectionStickerPrint( + collectionFk = collection.collectionFk, + labelCount = labelCount + ) + val printerName = + mobileApplication.dataStoreApp.readDataStoreKey(PRINTERNAME) + (getString(R.string.Imprimiendo) + printerName).toast(requireContext()) + } + ) + + } else { + viewModel.collectionStickerPrint( + collectionFk = collection.collectionFk, null + ) + + } + + } + + private fun showMistakeList(list: List) { + customDialogInput.dismiss() + listPlacementSupply = ArrayList() + list.forEach { + listPlacementSupply.add(BarcodeVO(code = it.description)) + } + + customDialogList.setTitle(getString(R.string.errorCause)) + customDialogList.hideTextInput().setKoButton(getString(R.string.cancel)) { + scanRequest() + requireActivity().hideKeyboard() + listPlacementSupply.clear() + customDialogList.dismiss() + + }.show() + + placementSupplyAdapter = + BarcodeAdapter(listPlacementSupply, object : OnBarcodeRowClickListener { + override fun onBarcodeRowClickListener(item: BarcodeVO) { + list.forEach { + if (it.description == item.code) { + + viewModel.saleMistakeAdd( + saleFk = mistakeSale?.saleFk!!, typeFk = it.id + ) + + getString(R.string.errorRegistered).toast(requireContext()) + customDialogList.dismiss() + } + } + + } + }, showDelete = false) + + customDialogList.getRecyclerView().adapter = placementSupplyAdapter + + customDialogList.getRecyclerView().layoutManager = + LinearLayoutManager(requireContext(), LinearLayoutManager.VERTICAL, false) + } + + private fun groupSaleGroup(salesList: ArrayList): MutableList { + val myMap = salesList.groupBy { it.saleGroupFk } + val myList: MutableList = mutableListOf() + + for ((key, value) in myMap.entries) { + if (key.isNullOrEmpty()) { // si no tiene saleGroup se añaden las líneas + for (s in value) { + myList.add(s) + } + } else { // si tiene saleGroup se crea el padre con el tamaño e indicando que es padre, como ejemplo se toma el primer elemento + /*crea padre*/ + if (value.size > 1) { + val mySale = SaleVO( + saleOrder = value[0].saleOrder, + workerFk = value[0].workerFk, + originalQuantity = null, + quantity = null, + rgb = null, + saleFk = value[0].saleFk, + saleGroupFk = value[0].saleGroupFk, + isPreControlled = value[0].isPreControlled, + isPrepared = value[0].isPrepared, + isPreviousPrepared = value[0].isPreviousPrepared, + isControlled = value[0].isControlled, + line3 = value[0].code ?: "", //6676 + picked = value[0].picked, + ticketFk = value[0].ticketFk, + level = value[0].level + )//prime elemento//hay que hacer una copia si no queda la referencia + mySale.totalSales = value.size //total líneas + mySale.isParent = true + value as MutableList + mySale.sonSales = + value.sortedWith(compareBy { it.picked }) as MutableList + mySale.line1 = "Previa: ${mySale.saleGroupFk}" + mySale.line2 = "Líneas: ${value.size}" + mySale.line3 = value[0].code ?: "" + mySale.placements = listOf(PlacementVO(shelving = value[0].code ?: "")) + + myList.add(mySale) + } else { + for (s in value) { + myList.add(s) + } + } + + } + + } + return myList + } +} \ No newline at end of file