Skip to content

Commit

Permalink
Add empty answer support
Browse files Browse the repository at this point in the history
  • Loading branch information
theMr17 committed Jan 27, 2024
1 parent 164f33b commit 1cf9a8f
Show file tree
Hide file tree
Showing 3 changed files with 58 additions and 4 deletions.
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package org.oppia.android.app.player.state.itemviewmodel

import androidx.annotation.StringRes
import androidx.databinding.Observable
import androidx.databinding.ObservableField
import androidx.recyclerview.widget.RecyclerView
Expand All @@ -13,6 +14,7 @@ import org.oppia.android.app.model.SubtitledHtml
import org.oppia.android.app.model.TranslatableHtmlContentId
import org.oppia.android.app.model.UserAnswer
import org.oppia.android.app.model.WrittenTranslationContext
import org.oppia.android.app.player.state.answerhandling.AnswerErrorCategory
import org.oppia.android.app.player.state.answerhandling.InteractionAnswerErrorOrAvailabilityCheckReceiver
import org.oppia.android.app.player.state.answerhandling.InteractionAnswerHandler
import org.oppia.android.app.player.state.answerhandling.InteractionAnswerReceiver
Expand All @@ -21,8 +23,21 @@ import org.oppia.android.app.recyclerview.OnDragEndedListener
import org.oppia.android.app.recyclerview.OnItemDragListener
import org.oppia.android.app.translation.AppLanguageResourceHandler
import org.oppia.android.domain.translation.TranslationController
import org.oppia.android.R
import javax.inject.Inject

/** Enum to the store the errors of drag and drop sort interaction. */
enum class DragAndDropSortInteractionError(@StringRes private var error: Int?) {
VALID(error = null),
EMPTY_INPUT(error = R.string.drag_and_drop_interaction_empty_input);

/**
* Returns the string corresponding to this error's string resources, or null if there is none.
*/
fun getErrorMessageFromStringRes(resourceHandler: AppLanguageResourceHandler): String? =
error?.let(resourceHandler::getStringInLocale)
}

/** [StateItemViewModel] for drag drop & sort choice list. */
class DragAndDropSortInteractionViewModel private constructor(
val entityId: String,
Expand Down Expand Up @@ -55,25 +70,34 @@ class DragAndDropSortInteractionViewModel private constructor(
subtitledHtml.contentId to translatedHtml
}

private val _choiceItems: MutableList<DragDropInteractionContentViewModel> =
private val _originalChoiceItems: MutableList<DragDropInteractionContentViewModel> =
computeChoiceItems(contentIdHtmlMap, choiceSubtitledHtmls, this, resourceHandler)

private val _choiceItems = _originalChoiceItems.toMutableList()
val choiceItems: List<DragDropInteractionContentViewModel> = _choiceItems

private var pendingAnswerError: String? = null
private val isAnswerAvailable = ObservableField(false)
var errorMessage = ObservableField<String>("")

init {
val callback: Observable.OnPropertyChangedCallback =
object : Observable.OnPropertyChangedCallback() {
override fun onPropertyChanged(sender: Observable, propertyId: Int) {
interactionAnswerErrorOrAvailabilityCheckReceiver.onPendingAnswerErrorOrAvailabilityCheck(
pendingAnswerError = null,
inputAnswerAvailable = true
pendingAnswerError,
inputAnswerAvailable = true // Allow submission without arranging or merging items.
)
}
}
isAnswerAvailable.addOnPropertyChangedCallback(callback)
isAnswerAvailable.set(true) // For drag drop submit button will be enabled by default.
errorMessage.addOnPropertyChangedCallback(callback)

// Initializing with default values so that submit button is enabled by default.
interactionAnswerErrorOrAvailabilityCheckReceiver.onPendingAnswerErrorOrAvailabilityCheck(
pendingAnswerError = null,
inputAnswerAvailable = true
)
}

override fun onItemDragged(
Expand All @@ -97,6 +121,7 @@ class DragAndDropSortInteractionViewModel private constructor(
// Update the data list if once drag is complete and merge icons are displayed.
if (allowMultipleItemsInSamePosition) {
(adapter as BindableAdapter<*>).setDataUnchecked(_choiceItems)
checkPendingAnswerError(AnswerErrorCategory.REAL_TIME)
}
}

Expand Down Expand Up @@ -129,6 +154,20 @@ class DragAndDropSortInteractionViewModel private constructor(
this@DragAndDropSortInteractionViewModel.writtenTranslationContext
}.build()

/**
* It checks the pending error for the current drag and drop sort interaction, and correspondingly
* updates the error string based on the specified error category.
*/
override fun checkPendingAnswerError(category: AnswerErrorCategory): String? {
pendingAnswerError = when (category) {
AnswerErrorCategory.REAL_TIME -> null
AnswerErrorCategory.SUBMIT_TIME ->
getSubmitTimeError().getErrorMessageFromStringRes(resourceHandler)
}
errorMessage.set(pendingAnswerError)
return pendingAnswerError
}

/** Returns an HTML list containing all of the HTML string elements as items in the list. */
private fun convertItemsToAnswer(htmlItems: List<StringList>): ListOfSetsOfHtmlStrings {
return ListOfSetsOfHtmlStrings.newBuilder()
Expand Down Expand Up @@ -190,6 +229,13 @@ class DragAndDropSortInteractionViewModel private constructor(
(adapter as BindableAdapter<*>).setDataUnchecked(_choiceItems)
}

private fun getSubmitTimeError(): DragAndDropSortInteractionError {
return if (_originalChoiceItems == _choiceItems)
DragAndDropSortInteractionError.EMPTY_INPUT
else
DragAndDropSortInteractionError.VALID
}

/** Implementation of [StateItemViewModel.InteractionItemFactory] for this view model. */
class FactoryImpl @Inject constructor(
private val resourceHandler: AppLanguageResourceHandler,
Expand Down
7 changes: 7 additions & 0 deletions app/src/main/res/layout/drag_drop_interaction_item.xml
Original file line number Diff line number Diff line change
Expand Up @@ -67,5 +67,12 @@
app:draggableData="@{viewModel.choiceItems}"
app:onDragEnded="@{(adapter) -> viewModel.onDragEnded(adapter)}"
app:onItemDrag="@{(indexFrom, indexTo, adapter) -> viewModel.onItemDragged(indexFrom, indexTo, adapter)}" />

<TextView
android:id="@+id/drag_drop_interaction_error"
style="@style/InputInteractionErrorTextView"
android:text="@{viewModel.errorMessage}"
android:textColor="@color/component_color_shared_input_error_color"
android:visibility="@{viewModel.errorMessage.length()>0? View.VISIBLE : View.GONE}" />
</LinearLayout>
</layout>
1 change: 1 addition & 0 deletions app/src/main/res/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -447,6 +447,7 @@
<string name="return_to_lesson">Return to lesson</string>
<string name="explanation">Explanation:</string>
<string name="drag_and_drop_interaction_group_merge_hint">If two items are equal, merge them.</string>
<string name="drag_and_drop_interaction_empty_input">Arrange the boxes to continue.</string>
<string name="link_to_item_below">Link to item %s</string>
<string name="unlink_items">Unlink items at %s</string>
<string name="move_item_down_content_description">Move item down to %s</string>
Expand Down

0 comments on commit 1cf9a8f

Please sign in to comment.