Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -66,39 +66,34 @@ class CategoryCreateViewModel : CommonViewModel<CategoryCreateViewModel.State>(S
}
}
private fun selectProduct(catalogProduct: CatalogProduct) {
if (!state.addedProducts.contains(catalogProduct)) {
update {
copy(
addedProducts = addedProducts + catalogProduct,
selectedProduct = catalogProduct,
items = items.filterNot { it.item == catalogProduct },
addedItems = addedItems + catalogProduct.mapToCategoryUiItems(
isSelected = true,
onDeleteClicked = {removeProduct(it)},
onSelectClicked = { _, _ -> }
),
categoryProducts = categoryProducts +
CategoryProduct(
id = requireNotNull(catalogProduct.product.id),
displayOrder = state.categoryProducts.size + 1
)
if (state.addedProducts.contains(catalogProduct)){ return }
update { copy(
addedProducts = addedProducts + catalogProduct,
selectedProduct = catalogProduct,
items = items.filterNot { it.item == catalogProduct },
addedItems = addedItems + catalogProduct.mapToCategoryUiItems(
isSelected = true,
onDeleteClicked = {removeProduct(it)},
onSelectClicked = { _, _ -> }
),
categoryProducts = categoryProducts +
CategoryProduct(
id = requireNotNull(catalogProduct.product.id),
displayOrder = state.categoryProducts.size + 1
)
}
}
) }
}
private fun removeProduct(catalogProduct: CatalogProduct) {
update {
copy(
addedProducts = addedProducts - catalogProduct,
categoryProducts = categoryProducts.filterNot { it.id == catalogProduct.product.id },
addedItems = addedItems.filterNot {it.item == catalogProduct },
items = listOf(catalogProduct.mapToCategoryUiItems(
isSelected = false,
onDeleteClicked = { removeProduct(it) },
onSelectClicked = { _, _ -> selectProduct(catalogProduct) }
)) + items
)
}
update { copy(
addedProducts = addedProducts - catalogProduct,
categoryProducts = categoryProducts.filterNot { it.id == catalogProduct.product.id },
addedItems = addedItems.filterNot {it.item == catalogProduct },
items = listOf(catalogProduct.mapToCategoryUiItems(
isSelected = false,
onDeleteClicked = { removeProduct(it) },
onSelectClicked = { _, _ -> selectProduct(catalogProduct) }
)) + items
) }
}

fun create() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,12 @@ import android.widget.Toast
import androidx.fragment.app.viewModels
import com.godaddy.commerce.sdk.util.isNotNullOrBlank
import com.godaddy.commerce.services.sample.R
import com.godaddy.commerce.services.sample.catalog.category.create.CategoryCreateViewModel
import com.godaddy.commerce.services.sample.common.extensions.bindTo
import com.godaddy.commerce.services.sample.common.extensions.launch
import com.godaddy.commerce.services.sample.common.extensions.observableField
import com.godaddy.commerce.services.sample.common.view.CommonFragment
import com.godaddy.commerce.services.sample.common.view.bindOnCommonViewModelUpdates
import com.godaddy.commerce.services.sample.databinding.CategoryUpdateFragmentBinding
import timber.log.Timber

class CategoryUpdateFragment :
CommonFragment<CategoryUpdateFragmentBinding>(R.layout.category_update_fragment) {
Expand All @@ -35,7 +33,7 @@ class CategoryUpdateFragment :
)
val allItems by observableField(
stateFlow = { viewModel.stateFlow },
map = { addedItems + items}
map = { addedItems + items }
)

override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
Expand All @@ -49,8 +47,8 @@ class CategoryUpdateFragment :
private fun bindToAddedItemsEvents() {
launch { viewModel.stateFlow.bindTo(
CategoryUpdateViewModel.State::addedItems) {
dataBinding.ProductRecyclerView.scrollToPosition(0)
}
dataBinding.ProductRecyclerView.scrollToPosition(0)
}
}
}

Expand All @@ -60,7 +58,6 @@ class CategoryUpdateFragment :
CategoryUpdateViewModel.State::updatedCategoryId
) { id ->
if (id.isNotNullOrBlank()) {
Timber.tag("test10").d("no")
return@bindTo Toast.makeText(
requireContext(),
"Category with id [${id}] was updated",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,6 @@ import timber.log.Timber

class TaxFragment : CommonFragment<TaxFragmentBinding>(R.layout.tax_fragment) {


private val viewModel: TaxViewModel by viewModels()

override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,39 +7,31 @@ import androidx.navigation.findNavController
import com.godaddy.commerce.catalog.model.CatalogTax
import com.godaddy.commerce.services.sample.R
import com.godaddy.commerce.services.sample.common.binding.RecyclerAdapterItem
import com.godaddy.commerce.services.sample.databinding.TaxAssociationItemBinding
import com.godaddy.commerce.services.sample.databinding.TaxItemBinding
import com.godaddy.commerce.taxes.models.AssociationItems
import java.util.*

data class TaxRecyclerItem(
override val item: CatalogTax,
override val onBinding: (binding: TaxItemBinding, position: Int, getItem: () -> CatalogTax) -> Unit = { _, _, _ -> },
) : RecyclerAdapterItem<CatalogTax, TaxItemBinding>(item, onBinding)
val amountString: String = if (item.tax.amount != null) (
item.tax.amount?.amount?.value.toString() + ' ' + item.tax.amount?.amount?.currencyCode
) else "N/A",
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should it be a localized string from R.string.*? Since we support multiple Locales

val percentageString: String = if (item.tax.amount == null) (
item.tax.percentage?.percentage.toString() + '%')
else "N/A",

val classificationCount: String = item.tax.classifications.orEmpty().size.toString(),
val overrideCount: String = item.tax.overrides.orEmpty().size.toString(),

override val onBinding: (binding: TaxItemBinding, position: Int, getItem: () -> CatalogTax) -> Unit = { _, _, _ -> }

) : RecyclerAdapterItem<CatalogTax, TaxItemBinding>(item, onBinding)

inline fun CatalogTax.mapToUiItems(): TaxRecyclerItem {
return TaxRecyclerItem(this) { binding, _, getItem ->
binding.updateBt.setOnClickListener {
it.findNavController().navigate(
resId = R.id.taxUpdateFragment,
args = bundleOf("id" to getItem().tax.id?.toString())
args = bundleOf("id" to getItem().tax.id)
)
}
}
}

data class TaxAssociationRecyclerItem(
override val item: AssociationItems,
override val onBinding: (binding: TaxAssociationItemBinding, position: Int, getItem: () -> AssociationItems) -> Unit = { _, _, _ -> }
) : RecyclerAdapterItem<AssociationItems, TaxAssociationItemBinding>(item, onBinding){
override fun getChangePayload(other: RecyclerAdapterItem<AssociationItems, TaxAssociationItemBinding>): Any = Unit
}


inline fun AssociationItems.mapToUiItems(crossinline deleteItemId: (UUID) -> Unit): TaxAssociationRecyclerItem {
return TaxAssociationRecyclerItem(this) { binding, _, getItem ->
binding.deleteBtn.setOnClickListener {
getItem().id?.let(deleteItemId)
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,16 +2,15 @@

package com.godaddy.commerce.services.sample.catalog.tax

import android.os.Bundle
import android.util.Log
import androidx.lifecycle.viewModelScope
import com.godaddy.commerce.catalog.CatalogIntents
import com.godaddy.commerce.catalog.TaxParams
import com.godaddy.commerce.catalog.model.CatalogTaxes
import com.godaddy.commerce.catalog.model.CatalogTax
import com.godaddy.commerce.common.DataSource
import com.godaddy.commerce.common.FilterBy
import com.godaddy.commerce.provider.catalog.CatalogContract
import com.godaddy.commerce.services.sample.catalog.onSuccess
import com.godaddy.commerce.services.sample.common.extensions.onError
import com.godaddy.commerce.sdk.catalog.TaxParamsExt
import com.godaddy.commerce.sdk.catalog.getCatalogTaxes
import com.godaddy.commerce.services.sample.common.extensions.subscribeOnUpdates
import com.godaddy.commerce.services.sample.common.viewmodel.CommonState
import com.godaddy.commerce.services.sample.common.viewmodel.CommonViewModel
Expand All @@ -20,16 +19,14 @@ import com.godaddy.commerce.services.sample.di.CommerceDependencyProvider
import kotlinx.coroutines.FlowPreview
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.onEach
import kotlinx.coroutines.suspendCancellableCoroutine
import timber.log.Timber

class TaxViewModel : CommonViewModel<TaxViewModel.State>(State()) {

private val serviceClient = CommerceDependencyProvider.getCatalogService(viewModelScope)

init {
loadTaxes()

// CS sends an event when data was changed. Subscribe on it and refresh the list.
CommerceDependencyProvider.getContext().subscribeOnUpdates(
CatalogIntents.ACTION_TAXES_CHANGED
).onEach {
Expand All @@ -40,26 +37,19 @@ class TaxViewModel : CommonViewModel<TaxViewModel.State>(State()) {
fun loadTaxes() {
execute {
val service = serviceClient.getService().getOrThrow()
val bundle = Bundle().apply {
// data source defines data provider: local db, remote or remote only if there are no data in local db.
// It is better to use REMOTE_IF_EMPTY in most cases to improve UX and performance.
putParcelable(TaxParams.DATA_SOURCE, DataSource.REMOTE_IF_EMPTY)

// Add pagination to improve UX and avoid TooLargeTransactionException
putInt(TaxParams.PAGE_OFFSET, 0)
putInt(TaxParams.PAGE_SIZE, 100)

// sorting is optional. List can be sorted by any column in database.
putString(TaxParams.SORT_BY, CatalogContract.Tax.Columns.UPDATED_AT)

// filter is optional. In this example we do showing taxes which are enabled.
putParcelable(TaxParams.FILTER_BY, FilterBy(CatalogContract.Tax.Columns.STATUS, "1", FilterBy.ComparisonOperator.EQUAL))
}
val response = suspendCancellableCoroutine<CatalogTaxes?> {
service.getCatalogTaxes(bundle, it.onSuccess(), it.onError())
}
val bundle = TaxParamsExt.toBundle(
dataSource = DataSource.REMOTE_IF_EMPTY,
pageOffset = 0,
pageSize = 100,
sortBy = CatalogContract.Tax.Columns.UPDATED_AT,
includeClassification = true,
includeOverrides = true,

)
val response = service.getCatalogTaxes(bundle)
update { copy(items = response?.taxes.orEmpty().map { it.mapToUiItems() }) }
}

}

data class State(
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package com.godaddy.commerce.services.sample.catalog.tax.create

import android.os.Bundle
import android.util.Log
import android.view.View
import android.widget.Toast
import androidx.fragment.app.viewModels
Expand All @@ -13,6 +14,9 @@ import com.godaddy.commerce.services.sample.common.extensions.observableField
import com.godaddy.commerce.services.sample.common.view.CommonFragment
import com.godaddy.commerce.services.sample.common.view.bindOnCommonViewModelUpdates
import com.godaddy.commerce.services.sample.databinding.TaxCreateFragmentBinding
import com.godaddy.commerce.services.sample.catalog.tax.create.TaxCreateViewModel.DialogType
import com.godaddy.commerce.services.sample.catalog.tax.update.TaxUpdateViewModel
import timber.log.Timber

class TaxCreateFragment :
CommonFragment<TaxCreateFragmentBinding>(R.layout.tax_create_fragment) {
Expand All @@ -23,21 +27,23 @@ class TaxCreateFragment :
stateFlow = { viewModel.stateFlow },
map = TaxCreateViewModel.State::createTaxOverride
)

val types by observableField(
val showTaxClassification by observableField(
stateFlow = { viewModel.stateFlow },
map = TaxCreateViewModel.State::createTaxClassification
)
val taxTypes by observableField(
stateFlow = { viewModel.stateFlow },
map = TaxCreateViewModel.State::label
map = TaxCreateViewModel.State::types
)
val taxTypePos by observableField(
stateFlow = { viewModel.stateFlow },
map = { taxType.let{ types.indexOf(it)} }
)

override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
bindOnCommonViewModelUpdates(viewModel)
launch {
viewModel.stateFlow.bindTo(
map = { products to showProductDialog },
update = ::showProductsDialog
)
}
bindToTaxDialogEvents()
launch {
viewModel.stateFlow.bindTo(TaxCreateViewModel.State::createdId) { id ->
id ?: return@bindTo
Expand All @@ -49,15 +55,24 @@ class TaxCreateFragment :
}
}
}
private fun bindToTaxDialogEvents(){
launch { viewModel.stateFlow.bindTo(
keySelector = { it.dialogType },
map = { this },
update = {
if (it.dialogType != null && it.dialogType != DialogType.NO_SHOW){
handleProductDialog(it.dialogList, it.dialogType)
}


private fun showProductsDialog(pair: Pair<List<CatalogProduct>, Boolean>) {
if (pair.second.not()) return
}
) }
}
private fun handleProductDialog(products: List<CatalogProduct>, dialogType: DialogType) {
requireContext().dialogBuilder(
"Select Product",
items = pair.first,
extras = dialogType,
items = products,
map = { it.product.label },
onSelected = viewModel::selectProduct
).setOnDismissListener { viewModel.hideProductsDialog() }.create().show()
}
}
onSelected = viewModel::handleProduct
).setOnDismissListener { viewModel.hideDialog() }.create().show()}
}
Loading