Create a dedicated factory for PollOptionViewState

This commit is contained in:
Maxime NATUREL 2023-01-19 17:22:37 +01:00
parent 96252ec2af
commit 91904a3e8f
3 changed files with 95 additions and 60 deletions

View file

@ -19,7 +19,6 @@ package im.vector.app.features.home.room.detail.timeline.factory
import im.vector.app.R
import im.vector.app.core.resources.StringProvider
import im.vector.app.features.home.room.detail.timeline.item.MessageInformationData
import im.vector.app.features.home.room.detail.timeline.item.PollOptionViewState
import im.vector.app.features.home.room.detail.timeline.item.PollResponseData
import im.vector.app.features.poll.PollViewState
import org.matrix.android.sdk.api.extensions.orFalse
@ -29,6 +28,7 @@ import javax.inject.Inject
class PollItemViewStateFactory @Inject constructor(
private val stringProvider: StringProvider,
private val pollOptionViewStateFactory: PollOptionViewStateFactory,
) {
fun create(
@ -40,7 +40,6 @@ class PollItemViewStateFactory @Inject constructor(
val question = pollCreationInfo?.question?.getBestQuestion().orEmpty()
val pollResponseSummary = informationData.pollResponseAggregatedSummary
val winnerVoteCount = pollResponseSummary?.winnerVoteCount
val totalVotes = pollResponseSummary?.totalVotes ?: 0
return when {
@ -48,7 +47,7 @@ class PollItemViewStateFactory @Inject constructor(
createSendingPollViewState(question, pollCreationInfo)
}
informationData.pollResponseAggregatedSummary?.isClosed.orFalse() -> {
createEndedPollViewState(question, pollCreationInfo, pollResponseSummary, totalVotes, winnerVoteCount)
createEndedPollViewState(question, pollCreationInfo, pollResponseSummary, totalVotes)
}
pollContent.getBestPollCreationInfo()?.isUndisclosed().orFalse() -> {
createUndisclosedPollViewState(question, pollCreationInfo, pollResponseSummary)
@ -67,12 +66,7 @@ class PollItemViewStateFactory @Inject constructor(
question = question,
votesStatus = stringProvider.getString(R.string.poll_no_votes_cast),
canVote = false,
optionViewStates = pollCreationInfo?.answers?.map { answer ->
PollOptionViewState.PollSending(
optionId = answer.id ?: "",
optionAnswer = answer.getBestAnswer() ?: ""
)
},
optionViewStates = pollOptionViewStateFactory.createPollSendingOptions(pollCreationInfo),
)
}
@ -81,7 +75,6 @@ class PollItemViewStateFactory @Inject constructor(
pollCreationInfo: PollCreationInfo?,
pollResponseSummary: PollResponseData?,
totalVotes: Int,
winnerVoteCount: Int?,
): PollViewState {
val totalVotesText = if (pollResponseSummary?.hasEncryptedRelatedEvents.orFalse()) {
stringProvider.getString(R.string.unable_to_decrypt_some_events_in_poll)
@ -92,17 +85,7 @@ class PollItemViewStateFactory @Inject constructor(
question = question,
votesStatus = totalVotesText,
canVote = false,
// TODO extract into helper method or mapper
optionViewStates = pollCreationInfo?.answers?.map { answer ->
val voteSummary = pollResponseSummary?.getVoteSummaryOfAnOption(answer.id ?: "")
PollOptionViewState.PollEnded(
optionId = answer.id ?: "",
optionAnswer = answer.getBestAnswer() ?: "",
voteCount = voteSummary?.total ?: 0,
votePercentage = voteSummary?.percentage ?: 0.0,
isWinner = winnerVoteCount != 0 && voteSummary?.total == winnerVoteCount
)
},
optionViewStates = pollOptionViewStateFactory.createPollEndedOptions(pollCreationInfo, pollResponseSummary),
)
}
@ -115,14 +98,7 @@ class PollItemViewStateFactory @Inject constructor(
question = question,
votesStatus = stringProvider.getString(R.string.poll_undisclosed_not_ended),
canVote = true,
optionViewStates = pollCreationInfo?.answers?.map { answer ->
val isMyVote = pollResponseSummary?.myVote == answer.id
PollOptionViewState.PollUndisclosed(
optionId = answer.id ?: "",
optionAnswer = answer.getBestAnswer() ?: "",
isSelected = isMyVote
)
},
optionViewStates = pollOptionViewStateFactory.createPollUndisclosedOptions(pollCreationInfo, pollResponseSummary),
)
}
@ -141,17 +117,7 @@ class PollItemViewStateFactory @Inject constructor(
question = question,
votesStatus = totalVotesText,
canVote = true,
optionViewStates = pollCreationInfo?.answers?.map { answer ->
val isMyVote = pollResponseSummary?.myVote == answer.id
val voteSummary = pollResponseSummary?.getVoteSummaryOfAnOption(answer.id ?: "")
PollOptionViewState.PollVoted(
optionId = answer.id ?: "",
optionAnswer = answer.getBestAnswer() ?: "",
voteCount = voteSummary?.total ?: 0,
votePercentage = voteSummary?.percentage ?: 0.0,
isSelected = isMyVote
)
},
optionViewStates = pollOptionViewStateFactory.createPollVotedOptions(pollCreationInfo, pollResponseSummary),
)
}
@ -169,12 +135,7 @@ class PollItemViewStateFactory @Inject constructor(
question = question,
votesStatus = totalVotesText,
canVote = true,
optionViewStates = pollCreationInfo?.answers?.map { answer ->
PollOptionViewState.PollReady(
optionId = answer.id ?: "",
optionAnswer = answer.getBestAnswer() ?: ""
)
},
optionViewStates = pollOptionViewStateFactory.createPollReadyOptions(pollCreationInfo),
)
}
}

View file

@ -0,0 +1,84 @@
/*
* Copyright (c) 2023 New Vector Ltd
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package im.vector.app.features.home.room.detail.timeline.factory
import im.vector.app.features.home.room.detail.timeline.item.PollOptionViewState
import im.vector.app.features.home.room.detail.timeline.item.PollResponseData
import org.matrix.android.sdk.api.session.room.model.message.PollCreationInfo
import javax.inject.Inject
// TODO add unit tests
class PollOptionViewStateFactory @Inject constructor() {
fun createPollEndedOptions(pollCreationInfo: PollCreationInfo?, pollResponseData: PollResponseData?): List<PollOptionViewState.PollEnded> {
val winnerVoteCount = pollResponseData?.winnerVoteCount
return pollCreationInfo?.answers?.map { answer ->
val voteSummary = pollResponseData?.getVoteSummaryOfAnOption(answer.id ?: "")
PollOptionViewState.PollEnded(
optionId = answer.id.orEmpty(),
optionAnswer = answer.getBestAnswer().orEmpty(),
voteCount = voteSummary?.total ?: 0,
votePercentage = voteSummary?.percentage ?: 0.0,
isWinner = winnerVoteCount != 0 && voteSummary?.total == winnerVoteCount
)
} ?: emptyList()
}
fun createPollSendingOptions(pollCreationInfo: PollCreationInfo?): List<PollOptionViewState.PollSending> {
return pollCreationInfo?.answers?.map { answer ->
PollOptionViewState.PollSending(
optionId = answer.id.orEmpty(),
optionAnswer = answer.getBestAnswer().orEmpty(),
)
} ?: emptyList()
}
fun createPollUndisclosedOptions(pollCreationInfo: PollCreationInfo?, pollResponseData: PollResponseData?): List<PollOptionViewState.PollUndisclosed> {
return pollCreationInfo?.answers?.map { answer ->
val isMyVote = pollResponseData?.myVote == answer.id
PollOptionViewState.PollUndisclosed(
optionId = answer.id.orEmpty(),
optionAnswer = answer.getBestAnswer().orEmpty(),
isSelected = isMyVote
)
} ?: emptyList()
}
fun createPollVotedOptions(pollCreationInfo: PollCreationInfo?, pollResponseData: PollResponseData?): List<PollOptionViewState.PollVoted> {
return pollCreationInfo?.answers?.map { answer ->
val isMyVote = pollResponseData?.myVote == answer.id
val voteSummary = pollResponseData?.getVoteSummaryOfAnOption(answer.id ?: "")
PollOptionViewState.PollVoted(
optionId = answer.id.orEmpty(),
optionAnswer = answer.getBestAnswer().orEmpty(),
voteCount = voteSummary?.total ?: 0,
votePercentage = voteSummary?.percentage ?: 0.0,
isSelected = isMyVote
)
} ?: emptyList()
}
fun createPollReadyOptions(pollCreationInfo: PollCreationInfo?): List<PollOptionViewState.PollReady> {
return pollCreationInfo?.answers?.map { answer ->
PollOptionViewState.PollReady(
optionId = answer.id ?: "",
optionAnswer = answer.getBestAnswer() ?: ""
)
} ?: emptyList()
}
}

View file

@ -17,8 +17,8 @@
package im.vector.app.features.roomprofile.polls.list.ui
import im.vector.app.core.extensions.getVectorLastMessageContent
import im.vector.app.features.home.room.detail.timeline.factory.PollOptionViewStateFactory
import im.vector.app.features.home.room.detail.timeline.helper.PollResponseDataFactory
import im.vector.app.features.home.room.detail.timeline.item.PollOptionViewState
import im.vector.app.features.home.room.detail.timeline.item.PollResponseData
import org.matrix.android.sdk.api.session.room.model.message.MessagePollContent
import org.matrix.android.sdk.api.session.room.timeline.TimelineEvent
@ -27,6 +27,7 @@ import javax.inject.Inject
// TODO add unit tests
class PollSummaryMapper @Inject constructor(
private val pollResponseDataFactory: PollResponseDataFactory,
private val pollOptionViewStateFactory: PollOptionViewStateFactory,
) {
fun map(timelineEvent: TimelineEvent): PollSummary {
@ -42,7 +43,7 @@ class PollSummaryMapper @Inject constructor(
pollResponseData = pollResponseData
)
} else {
throw IllegalStateException("expected MessagePollContent")
throw IllegalStateException("missing mandatory info about poll event with id=$eventId")
}
}
@ -55,23 +56,12 @@ class PollSummaryMapper @Inject constructor(
val pollCreationInfo = messagePollContent.getBestPollCreationInfo()
val pollTitle = pollCreationInfo?.question?.getBestQuestion().orEmpty()
return if (pollResponseData.isClosed) {
val winnerVoteCount = pollResponseData.winnerVoteCount
PollSummary.EndedPoll(
id = eventId,
creationTimestamp = creationTimestamp,
title = pollTitle,
totalVotes = pollResponseData.totalVotes,
// TODO mutualise this with PollItemViewStateFactory
winnerOptions = pollCreationInfo?.answers?.map { answer ->
val voteSummary = pollResponseData.getVoteSummaryOfAnOption(answer.id ?: "")
PollOptionViewState.PollEnded(
optionId = answer.id ?: "",
optionAnswer = answer.getBestAnswer() ?: "",
voteCount = voteSummary?.total ?: 0,
votePercentage = voteSummary?.percentage ?: 0.0,
isWinner = winnerVoteCount != 0 && voteSummary?.total == winnerVoteCount
)
} ?: emptyList()
winnerOptions = pollOptionViewStateFactory.createPollEndedOptions(pollCreationInfo, pollResponseData)
)
} else {
PollSummary.ActivePoll(