Skip to content

Commit

Permalink
Merge branch 'develop' into refactor_topic_to_use_profileId
Browse files Browse the repository at this point in the history
  • Loading branch information
adhiamboperes authored Dec 23, 2024
2 parents d994616 + 3ada868 commit de8ead3
Show file tree
Hide file tree
Showing 3 changed files with 141 additions and 1 deletion.
Original file line number Diff line number Diff line change
@@ -1,10 +1,38 @@
package org.oppia.android.app.player.state.itemviewmodel

import android.text.Spannable
import android.text.SpannableStringBuilder

/** [StateItemViewModel] for content-card state. */
class ContentViewModel(
val htmlContent: CharSequence,
val gcsEntityId: String,
val hasConversationView: Boolean,
val isSplitView: Boolean,
val supportsConceptCards: Boolean
) : StateItemViewModel(ViewType.CONTENT)
) : StateItemViewModel(ViewType.CONTENT) {

private val underscoreRegex = Regex("(?<=\\s|[,.;?!])_{3,}(?=\\s|[,.;?!])")
private val replacementText = "Blank"

/**
* Replaces "2+ underscores, with space/punctuation on both sides" in the input text with a
* replacement string "blank", returning a Spannable.
* Adjusts offsets to handle text length changes during replacements.
*/
fun replaceRegexWithBlank(inputText: CharSequence): Spannable {
val spannableStringBuilder = SpannableStringBuilder(inputText)
val matches = underscoreRegex.findAll(inputText)
var lengthOffset = 0

for (match in matches) {
val matchStart = match.range.first + lengthOffset
val matchEnd = match.range.last + 1 + lengthOffset
spannableStringBuilder.replace(matchStart, matchEnd, replacementText)

// Adjust offset due to change in length (difference between old and new text length)
lengthOffset += replacementText.length - (matchEnd - matchStart)
}
return spannableStringBuilder
}
}
1 change: 1 addition & 0 deletions app/src/main/res/layout/content_item.xml
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@
android:minWidth="48dp"
android:minHeight="48dp"
android:text="@{htmlContent}"
android:contentDescription="@{viewModel.replaceRegexWithBlank(htmlContent)}"
android:textColor="@color/component_color_shared_primary_text_color"
android:textColorLink="@color/component_color_shared_link_text_color"
android:textSize="16sp"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,7 @@ import org.oppia.android.domain.platformparameter.PlatformParameterSingletonModu
import org.oppia.android.domain.profile.ProfileManagementController
import org.oppia.android.domain.question.QuestionModule
import org.oppia.android.domain.topic.FRACTIONS_EXPLORATION_ID_1
import org.oppia.android.domain.topic.RATIOS_EXPLORATION_ID_0
import org.oppia.android.domain.topic.TEST_EXPLORATION_ID_13
import org.oppia.android.domain.topic.TEST_EXPLORATION_ID_2
import org.oppia.android.domain.topic.TEST_EXPLORATION_ID_4
Expand Down Expand Up @@ -5206,6 +5207,110 @@ class StateFragmentTest {
}
}

@Test
fun testStateFragment_contentDescription_replaceUnderscoresWithBlank() {
setUpTestWithLanguageSwitchingFeatureOff()
launchForExploration(RATIOS_EXPLORATION_ID_0, shouldSavePartialProgress = false).use {
startPlayingExploration()

playThroughRatioExplorationState1()
playThroughRatioExplorationState2()
playThroughRatioExplorationState3()
playThroughRatioExplorationState4()
playThroughRatioExplorationState5()
playThroughRatioExplorationState6()
playThroughRatioExplorationState7()
playThroughRatioExplorationState8()
playThroughRatioExplorationState9()
playThroughRatioExplorationState10()
playThroughRatioExplorationState11()
playThroughRatioExplorationState12()
playThroughRatioExplorationState13()
playThroughRatioExplorationState14()

val expectedDescription = "James turned the page, and saw a recipe for banana smoothie." +
" Yummy!\n\n2 cups of milk and 1 cup of banana puree \n\n“I can make this,” he said." +
" “We’ll need to mix milk and banana puree in the ratio Blank.”\n\nCan you complete" +
" James’s sentence? What is the ratio of milk to banana puree?”"

onView(withId(R.id.content_text_view))
.check(matches(withContentDescription(expectedDescription)))
}
}

private fun playThroughRatioExplorationState1() {
clickContinueInteractionButton()
}

private fun playThroughRatioExplorationState2() {
clickContinueInteractionButton()
}

private fun playThroughRatioExplorationState3() {
clickContinueInteractionButton()
}

private fun playThroughRatioExplorationState4() {
clickContinueInteractionButton()
}

private fun playThroughRatioExplorationState5() {
clickContinueInteractionButton()
}

private fun playThroughRatioExplorationState6() {
typeTextInput("2 to 5")
clickSubmitAnswerButton()
clickContinueNavigationButton()
}

private fun playThroughRatioExplorationState7() {
typeTextInput("3 to 1")
clickSubmitAnswerButton()
clickContinueNavigationButton()
}

private fun playThroughRatioExplorationState8() {
typeTextInput("2:3")
clickSubmitAnswerButton()
clickContinueNavigationButton()
}

private fun playThroughRatioExplorationState9() {
typeTextInput("5:2")
clickSubmitAnswerButton()
clickContinueNavigationButton()
}

private fun playThroughRatioExplorationState10() {
clickContinueInteractionButton()
}

private fun playThroughRatioExplorationState11() {
selectMultipleChoiceOption(
2,
"The relative relationship between the amounts of different things."
)
clickSubmitAnswerButton()
clickContinueNavigationButton()
}

private fun playThroughRatioExplorationState12() {
clickContinueInteractionButton()
}

private fun playThroughRatioExplorationState13() {
typeTextInput("1:4")
clickSubmitAnswerButton()
clickContinueNavigationButton()
}

private fun playThroughRatioExplorationState14() {
typeTextInput("1:4")
clickSubmitAnswerButton()
clickContinueNavigationButton()
}

private fun addShadowMediaPlayerException(dataSource: Any, exception: Exception) {
val classLoader = StateFragmentTest::class.java.classLoader!!
val shadowMediaPlayerClass = classLoader.loadClass("org.robolectric.shadows.ShadowMediaPlayer")
Expand Down Expand Up @@ -5793,7 +5898,13 @@ class StateFragmentTest {
explorationId = FRACTIONS_EXPLORATION_ID_1, audioFileName = "content-en-ouqm7j21vt8.mp3"
)
) { "Failed to create audio data source." }
val dataSource2 = checkNotNull(
createAudioDataSource(
explorationId = RATIOS_EXPLORATION_ID_0, audioFileName = "content-en-057j51i2es.mp3"
)
) { "Failed to create audio data source." }
addShadowMediaPlayerException(dataSource, IOException("Test does not have networking"))
addShadowMediaPlayerException(dataSource2, IOException("Test does not have networking"))
}
}

Expand Down

0 comments on commit de8ead3

Please sign in to comment.