From 3c5545bdb6b1189ba23e435ae18a720102c30021 Mon Sep 17 00:00:00 2001 From: "arthur.valin" Date: Sat, 13 Jan 2024 12:28:20 +0100 Subject: [PATCH 1/3] Bet result page --- src/app/build.gradle.kts | 16 +- src/app/keys/keystore.jks | Bin 2487 -> 0 bytes src/app/keys/keystore.properties | 2 - src/app/keys/private_key.pepk | Bin 1776 -> 0 bytes src/app/proguard-rules.pro | 17 +- .../fr/iut/alldev/allin/test/mock/Bets.kt | 22 +- .../fr/iut/alldev/allin/vo/bet/BetVOTest.kt | 31 +- .../BetVOTestVisitor.kt | 15 +- .../allin/keystore/AllInKeystoreManager.kt | 5 +- .../keystore/impl/AllInKeystoreManagerImpl.kt | 11 +- .../java/fr/iut/alldev/allin/test/TestTags.kt | 3 +- .../java/fr/iut/alldev/allin/theme/Color.kt | 2 + .../java/fr/iut/alldev/allin/theme/Theme.kt | 45 +- .../java/fr/iut/alldev/allin/theme/Type.kt | 50 +- .../fr/iut/alldev/allin/ui/bet/BetScreen.kt | 4 +- .../allin/ui/bet/components/BetScreenCard.kt | 2 +- .../ui/bet/components/BetScreenPopularCard.kt | 6 +- .../allin/ui/betHistory/BetHistoryScreen.kt | 4 +- .../components/BetHistoryScreenCard.kt | 44 +- .../ui/betResult/BetResultBottomSheet.kt | 172 + .../components/BetResultBottomSheetBetCard.kt | 60 + .../BetResultBottomSheetBetCardStats.kt | 111 + ...ultBottomSheetBetContentCongratulations.kt | 71 + .../BetResultBottomSheetContentCoinAmount.kt | 79 + .../ui/betStatus/BetStatusBottomSheet.kt | 12 +- .../BetStatusParticipationBottomSheet.kt | 29 +- .../betStatus/components/BetStatusWinner.kt | 7 +- .../betStatus/components/YesNoDetailsLine.kt | 5 +- .../ui/betStatus/components/YesNoStarBar.kt | 2 +- .../BetStatusBottomSheetBetDisplayer.kt} | 106 +- .../alldev/allin/ui/core/AllInAlertDialog.kt | 2 +- .../alldev/allin/ui/core/AllInBottomSheet.kt | 2 + .../fr/iut/alldev/allin/ui/core/AllInChip.kt | 2 +- .../alldev/allin/ui/core/AllInCoinCount.kt | 14 +- .../alldev/allin/ui/core/AllInDatePicker.kt | 2 +- .../allin/ui/core/AllInDetailsDrawer.kt | 2 +- .../alldev/allin/ui/core/AllInErrorLine.kt | 2 +- .../allin/ui/core/AllInRetractableCard.kt | 2 +- .../allin/ui/core/AllInSectionButton.kt | 4 +- .../alldev/allin/ui/core/AllInTextField.kt | 4 +- .../iut/alldev/allin/ui/core/AllInTextIcon.kt | 55 +- .../alldev/allin/ui/core/AllInTimePicker.kt | 2 +- .../iut/alldev/allin/ui/core/AllInTooltip.kt | 4 +- .../java/fr/iut/alldev/allin/ui/core/Icon.kt | 38 + .../iut/alldev/allin/ui/core/bet/BetCard.kt | 76 + .../allin/ui/core/bet/BetDateTimeChip.kt | 2 +- .../allin/ui/core/bet/BetDateTimeRow.kt | 2 +- .../allin/ui/core/bet/BetTitleHeader.kt | 4 +- .../allin/ui/core/snackbar/AllInSnackBar.kt | 2 +- .../iut/alldev/allin/ui/login/LoginScreen.kt | 10 +- .../fr/iut/alldev/allin/ui/main/MainScreen.kt | 40 +- .../iut/alldev/allin/ui/main/MainViewModel.kt | 15 + .../allin/ui/navigation/drawer/AllInDrawer.kt | 2 +- .../drawer/components/DrawerCell.kt | 2 +- .../drawer/components/DrawerHeaderStat.kt | 2 +- .../allin/ui/preview/BetPreviewProvider.kt | 51 + .../iut/alldev/allin/ui/preview/BetStatus.kt | 14 - .../ui/preview/BetStatusPreviewProvider.kt | 8 + .../preview/BetWithStatusPreviewProvider.kt | 53 + .../allin/ui/register/RegisterScreen.kt | 10 +- .../alldev/allin/ui/welcome/WelcomeScreen.kt | 6 +- .../java/fr/iut/alldev/allin/vo/ViewObject.kt | 8 - .../java/fr/iut/alldev/allin/vo/Visitor.kt | 3 - .../iut/alldev/allin/vo/bet/BetDisplayer.kt | 27 + .../java/fr/iut/alldev/allin/vo/bet/BetVO.kt | 28 - .../allin/vo/bet/factory/BetVOFactory.kt | 30 - .../alldev/allin/vo/bet/visitor/BetVisitor.kt | 15 - .../src/main/res/drawable/allin_marquee.xml | 4307 +++++++++++++++++ .../main/res/font/plusjakartasans_bold.ttf | Bin 94784 -> 0 bytes .../res/font/plusjakartasans_extrabold.ttf | Bin 94788 -> 0 bytes .../res/font/plusjakartasans_extralight.ttf | Bin 94772 -> 0 bytes .../main/res/font/plusjakartasans_light.ttf | Bin 94796 -> 0 bytes .../main/res/font/plusjakartasans_medium.ttf | Bin 94816 -> 0 bytes .../main/res/font/plusjakartasans_regular.ttf | Bin 94764 -> 0 bytes .../res/font/plusjakartasans_semibold.ttf | Bin 94848 -> 0 bytes src/app/src/main/res/values-fr/strings.xml | 6 + src/app/src/main/res/values/font_certs.xml | 17 + src/app/src/main/res/values/strings.xml | 8 + .../fr/iut/alldev/allin/data/api/AllInApi.kt | 2 +- .../iut/alldev/allin/data/api/model/ApiBet.kt | 3 +- .../fr/iut/alldev/allin/data/model/bet/Bet.kt | 5 +- .../alldev/allin/data/model/bet/BetStatus.kt | 10 + .../data/repository/impl/BetRepositoryImpl.kt | 3 +- .../ReleaseModule.kt | 4 - .../ReleaseNetworkModule.kt | 2 +- src/gradle/libs.versions.toml | 9 +- src/keys/debug.keystore | Bin 0 -> 2779 bytes src/keys/keystore.properties | 4 + src/keys/release.keystore | Bin 0 -> 2775 bytes 89 files changed, 5430 insertions(+), 428 deletions(-) delete mode 100644 src/app/keys/keystore.jks delete mode 100644 src/app/keys/keystore.properties delete mode 100644 src/app/keys/private_key.pepk rename src/app/src/androidTest/java/fr/iut/alldev/allin/vo/bet/{visitor => displayer}/BetVOTestVisitor.kt (53%) create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/BetResultBottomSheet.kt create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetCard.kt create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetCardStats.kt create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetContentCongratulations.kt create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetContentCoinAmount.kt rename src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/{visitor/BetStatusBottomSheetDisplayBetVisitor.kt => vo/BetStatusBottomSheetBetDisplayer.kt} (72%) create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/core/Icon.kt create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetCard.kt create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt delete mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetStatus.kt create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetStatusPreviewProvider.kt create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt delete mode 100644 src/app/src/main/java/fr/iut/alldev/allin/vo/ViewObject.kt delete mode 100644 src/app/src/main/java/fr/iut/alldev/allin/vo/Visitor.kt create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt delete mode 100644 src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetVO.kt delete mode 100644 src/app/src/main/java/fr/iut/alldev/allin/vo/bet/factory/BetVOFactory.kt delete mode 100644 src/app/src/main/java/fr/iut/alldev/allin/vo/bet/visitor/BetVisitor.kt create mode 100644 src/app/src/main/res/drawable/allin_marquee.xml delete mode 100644 src/app/src/main/res/font/plusjakartasans_bold.ttf delete mode 100644 src/app/src/main/res/font/plusjakartasans_extrabold.ttf delete mode 100644 src/app/src/main/res/font/plusjakartasans_extralight.ttf delete mode 100644 src/app/src/main/res/font/plusjakartasans_light.ttf delete mode 100644 src/app/src/main/res/font/plusjakartasans_medium.ttf delete mode 100644 src/app/src/main/res/font/plusjakartasans_regular.ttf delete mode 100644 src/app/src/main/res/font/plusjakartasans_semibold.ttf create mode 100644 src/app/src/main/res/values/font_certs.xml create mode 100644 src/keys/debug.keystore create mode 100644 src/keys/keystore.properties create mode 100644 src/keys/release.keystore diff --git a/src/app/build.gradle.kts b/src/app/build.gradle.kts index d9b3b9f..bd7d3fb 100644 --- a/src/app/build.gradle.kts +++ b/src/app/build.gradle.kts @@ -10,7 +10,7 @@ plugins { } // Keystore -val keystorePropertiesFile = rootProject.file("app/keys/keystore.properties") +val keystorePropertiesFile = rootProject.file("keys/keystore.properties") val keystoreProperties = Properties() keystoreProperties.load(FileInputStream(keystorePropertiesFile)) @@ -33,11 +33,16 @@ android { } } + signingConfigs { + named(BuildType.DEBUG.name) { + storeFile = file(keystoreProperties["debugStoreFile"].toString()) + } register(BuildType.RELEASE.name) { - storeFile = file(keystoreProperties["store"].toString()) - storePassword = keystoreProperties["password"].toString() - keyPassword = keystoreProperties["password"].toString() + storeFile = file(keystoreProperties["releaseStoreFile"].toString()) + storePassword = keystoreProperties["passwordRelease"].toString() + keyAlias = keystoreProperties["aliasRelease"].toString() + keyPassword = keystoreProperties["passwordRelease"].toString() } } @@ -102,5 +107,6 @@ dependencies { androidTestImplementation(libs.test.androidx.junit) androidTestImplementation(libs.hilt.androidTesting) kaptAndroidTest(libs.hilt.androidCompiler) - + androidTestImplementation(libs.ui.test.junit) + debugImplementation(libs.ui.test.manifest) } \ No newline at end of file diff --git a/src/app/keys/keystore.jks b/src/app/keys/keystore.jks deleted file mode 100644 index bb4e75c73afc503f20db770b3aa682160c033150..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2487 zcma)+c{J1u8^>ptHDhcuWDg;JgfKUhMAurDAzVfgSwhNQjGZww}SWVz0H-*fMI|9ao^oaa2}`Fx-6^XC^JFjhjqP=LVbieQwA(2bz8f*HU$ z1V$Sefzk2|n*juP*?&p!Oc(*4dWK(}^-Bcve_Sj~U`P%Du6YK30UZB!z*zxHK;@s6 z1(1euCKue)53ETqjCV^LbXWCH!yf;ji@j}S&U2)KY?w2ROMJ3wJz zDHyv;1SZ>5!5|?eJDvmiWTO{GfPHe@uK#GC8SzF)SCC;TiBi5(*)v&?#Q*3dV#`i) z|DzV?PHCEt%(qixDq#G%ycXSR}FS_1nOu*F5r{=!IgFj-GL!8mIay)dKmAb^%e}GJheg zqqg+(nJDEHoWlHf=2>oQMK%nl04}{N^2J^Ke69^4gQbY+ts}QF0OtDhsLEhG8x<9w z{&dgSO+XHXATrW;(<_HFe=YID1_vZx*Q1*oDUX^%!)Eau-C^dM#{m;14caJLtj(+D zYk`tC9Hc1^5`X9IxHBx^aKb4U-6s5I-8H%zQ-h0p9M8CZS~%Zans(Z7eH&HkbzsNR zV9`FY%deN`A{}rf)i)(VY|WAgG3BcjSb1drbc>rI?>`RpEM0k9wyAqE z2H8qNiaCCUR`5p`+O69uRQ=KBz-rR$wQTK}J2C`WXykG$3h%KNg+>jFHxYF&cl}mO zf#F-ytJf6mmOXCam%hKxqM}wU)@;qbkq8GhMFqRBhK)L(M~SlE7+k&6Q1cD8##<3_ zEqQM*Z$WO3_g)iPlD`@A?m|OHlRR|KQ?4f zgIchVg1N4St201ZpL98X_g_}l^mXF14KY1bc2#?>){9Ybof5rP@SYQ9F zd+crc9E^f+!6FtYxQe(!bt`t?mKM={yflp*tbBp zlaP7?O{}$LW(`$q>=+Lnw!eu^&Dzh~r79M%xEbRjCx3wt=!XsNaAk9^P23{xmQ}Fw zNq{pH-hUui05uQdAHec;}Z#T{= zH}X)o-Vn5y0X=*ksgYNNCE8wSts(dJ#swAo>w2&SFYrM8fI?_zD zhb8zzin8*b-XqI?IY-Mi^a=AW zPw{j4qZd07=_`ErQZbE~jKi)rsG^Hk75bHrZV|Z`6&h%Oa%cX+Ot+zbjKC0PGKn~= z`0KMod36B&cU&@Z%CiVCf$$*LvvLNx1H%7ET=JYS4pV102O)W7)vJJ#qOvL=e+2*t z(A>X|7!WxGDESPLAYjnhi2O$Z|F4ji;M=WN&7YXkj#Y3*&pSRre&KKXe?r=N)!RFr zEI57 zQ0_Gc1&`KVfxAbKvuQ5}M%$EhB-IoTqsX0WSKY#mSU|>)bn&ER$H;6yzjTXyA-dzn z{olP73H2my&lw+kJzuI$93LG?6Zo2);>pK17<9)c*quQsv($=>IwbgK;AShj`eLt} z^oF<_I5?|Poja{JL9xj^VG*+h`n`;)FW;~pho?%jX@ebB+b}%t~oI+MzzNeNwo&! zN%-!Nx>y%fN$0R5Q}g%b?S0;*y`9jqcYTYcy^p?T*pXE^ z#Yl#szUY1!%A|aSo@Oz%Q~Z#}DlT(vl+r9@aWS4;hr&-IFU=(f)&ZL*V?dg`io}raZS7}UVLJz#{Wyp_>0Dt*KbB|w6q;~;l$~9^r zRvvW?e>))bcI*ZdiQ|R><4-gbTBQ6cKUt^D&;=)LccWA>)@S2>sK!$~uRhQo)K_x+ z!~-P|@83F>QY6`BzNK&uPzQtoMg&}%4GO`)K`>5^g`}D3p8LTfSFVWgGFW}C%!A#A eaZ>Ao!nF_dw<_9u0!1`SGW{cITM#HXBIhqz*LgDl diff --git a/src/app/keys/keystore.properties b/src/app/keys/keystore.properties deleted file mode 100644 index fe9ab09..0000000 --- a/src/app/keys/keystore.properties +++ /dev/null @@ -1,2 +0,0 @@ -store=keys/keystore.jks -password=placeYourBets \ No newline at end of file diff --git a/src/app/keys/private_key.pepk b/src/app/keys/private_key.pepk deleted file mode 100644 index be8173be51d3184121224f5be2dff08f231e5142..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1776 zcmVk$5rZS}76T7noQl%QvPUqR@QmC3P<=<~GQJ!M0aNrLC1{L0Bnv zk0>rA7z~voWh2xXqYhti!eRDv-bzAlvF8n8B7>nPlt(*5lMro_sYOHLIxFj?+=|~h zD3+S0*o>~ia-rB|M<)j-;+M|l+%W55)B%w@SQk~+VUcEk&@%4Rc5S)RSHd$mT+EeO zFM$#N_4mEhNZ6s|`+F9L7!i}+ZNWnAl;IMGevY^kb>Z)21s%4(3e_ZQ z&d^c}Y!wp+wQRStpMY7~u0EFCH3ncXyF=vLUWm)O(tG@(em)lBDbm^>$GHY<?#z z=tYm}^l2){csKvEK4mEQ!f&o-EA{xP7&H_Gr#OCP+PaJ0WzabP0`owKaAAJcrGutS z!^U;+$>ytUdc(Z@`l!TRx$;pfixq;&Mv5$*K{Jw@s!mFYGrI();V;EnVoGQ=Z5=ehmOle&^bbToOsSumzy2sYpuh4{l=q}CuEbLML*K?dmn$W2PV7&Pfw z7KV(S7H?yh4GYwkgMxTSYLQQC_PsLuI2F6|znt?CeJ8_ZTIKEtScH*b;!j0d1{Vt} ziII-K#t5@Ij{h~WG5R|`>`Ija{zGj%Lq3}JpadBSaQV!Fvla?DQyQhT!R{H6Css_ubJiWLC3loTYYWrgEWn0(W zzEj|K>4~L6{Qu3|;9a{FhAx~MsgB+Z)!TWAZ9Ck6%I))?w(6e}dUy;ZSmz~$v5*i6 zimKx=?R|5(VbtL7@_L6&3^DRYWB2h8RKxl}7t%FmLk24n0WDW)?eQoF;Cy5l2#aX* zr;EvMlfMRx)WwHf@oe1llZQKCwWiV|F4zVZSNYQAF$N@wllK_(H`gLi{YO#O! z02*8Cj2}I%u)%r-;nhU;@JPSpj#>rw#uJVi^LDj51ym`T(1wdCKg)kq^D>Ar#cm2D zp`^lhevgVYgr>?JmU8m_;qkvnny2`hYZu#MlU$z8r8#;1^P7A%vah@-yUj#2%3Ib1 zO8vgr=6PmSphjAX=W6bhqi4tlPb4%=A;&mJHzEPhc#VNt>Hdu&5Ft#=t4j^a`xue6%6WRmNio{{ z|AGas_{1+v-^pDh+LIAk+pOa}+dd!@nP=cxXQo zMody-mZIc+ea!~#^>6=lp-1cYtSfOs$Tobb^N;f?P>F(X@lltJ)M*Y+i-tpd1Z1ac(_CMWCH+>FYz(N1~IyJEC(4}f9e zKnD Unit +) { + AllInBottomSheet( + sheetVisibility = sheetVisibility, + onDismiss = onDismiss, + state = state, + dragHandle = null + ) { + BetResultBottomSheetContent( + username = username, + coinAmount = coinAmount, + bet = bet, + stake = stake, + winnings = winnings, + odds = odds, + onClose = onDismiss + ) + } +} + +@Composable +fun BetResultBottomSheetContent( + username: String, + coinAmount: Int, + bet: Bet, + stake: Int, + winnings: Int, + odds: Float, + onClose: () -> Unit +) { + Box( + modifier = Modifier + .fillMaxSize() + .background(AllInTheme.colors.allInMainGradientReverse), + ) { + Icon( + painter = painterResource(id = R.drawable.allin_marquee), + contentDescription = null, + modifier = Modifier + .fillMaxSize() + .rotate(11f) + .scale(1.2f) + .offset(x = (-24).dp) + .basicMarquee(spacing = MarqueeSpacing(0.dp)), + tint = AllInTheme.colors.white.copy(alpha = .05f) + ) + Box( + modifier = Modifier + .fillMaxSize() + .padding(16.dp) + ) { + IconButton( + onClick = onClose, + modifier = Modifier + .size(24.dp) + .align(Alignment.TopStart) + ) { + Icon( + imageVector = Icons.Default.Close, + tint = AllInTheme.colors.white, + contentDescription = null, + modifier = Modifier.size(24.dp) + ) + } + + Icon( + painter = painterResource(R.drawable.allin), + contentDescription = null, + tint = AllInTheme.colors.white, + modifier = Modifier + .size(40.dp) + .align(Alignment.TopCenter) + ) + + Column( + modifier = Modifier.align(Alignment.Center), + verticalArrangement = Arrangement.spacedBy(48.dp), + horizontalAlignment = Alignment.CenterHorizontally + ) { + + BetResultBottomSheetContentCongratulations(username = username) + BetResultBottomSheetContentCoinAmount(amount = coinAmount) + BetResultBottomSheetBetCard( + title = bet.phrase, + creator = bet.creator, + category = bet.theme, + date = bet.endBetDate.formatToMediumDateNoYear(), + time = bet.endBetDate.formatToTime(), + status = bet.betStatus, + stake = stake, + winnings = winnings, + odds = odds + + ) + } + } + } +} + +@Preview +@Preview(widthDp = 800, heightDp = 1280) +@Composable +private fun BetResultBottomSheetContentPreview() { + AllInTheme { + BetResultBottomSheetContent( + username = "Pseudo", + coinAmount = 3976, + bet = YesNoBet( + theme = "Theme", + phrase = "Phrase", + endRegisterDate = ZonedDateTime.now(), + endBetDate = ZonedDateTime.now(), + isPublic = true, + betStatus = BetStatus.InProgress, + creator = "creator", + ), + stake = 4175, + winnings = 2600, + odds = 6.7f + ) { + + } + } +} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetCard.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetCard.kt new file mode 100644 index 0000000..d0050dc --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetCard.kt @@ -0,0 +1,60 @@ +package fr.iut.alldev.allin.ui.betResult.components + +import android.content.res.Configuration +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.tooling.preview.Preview +import fr.iut.alldev.allin.data.model.bet.BetFinishedStatus +import fr.iut.alldev.allin.data.model.bet.BetStatus +import fr.iut.alldev.allin.theme.AllInTheme +import fr.iut.alldev.allin.ui.core.bet.BetCard + +@Composable +fun BetResultBottomSheetBetCard( + modifier: Modifier = Modifier, + title: String, + creator: String, + category: String, + date: String, + time: String, + status: BetStatus, + stake: Int, + winnings: Int, + odds: Float +) { + BetCard( + title = title, + creator = creator, + category = category, + date = date, + time = time, + status = status, + modifier = modifier + ) { + BetResultBottomSheetBetCardStats( + stake = stake, + winnings = winnings, + odds = odds + ) + } +} + + +@Preview +@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +private fun BetResultBottomSheetBetCardPreview() { + AllInTheme { + BetResultBottomSheetBetCard( + creator = "Creator", + category = "Category", + title = "Title", + date = "Date", + time = "Time", + status = BetStatus.Finished(BetFinishedStatus.WON), + stake = 2446, + winnings = 6930, + odds = 2.3f + ) + } +} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetCardStats.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetCardStats.kt new file mode 100644 index 0000000..4a5aae6 --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetCardStats.kt @@ -0,0 +1,111 @@ +package fr.iut.alldev.allin.ui.betResult.components + +import android.content.res.Configuration +import androidx.compose.foundation.background +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import fr.iut.alldev.allin.R +import fr.iut.alldev.allin.theme.AllInTheme +import fr.iut.alldev.allin.ui.core.AllInCard +import fr.iut.alldev.allin.ui.core.AllInCoinCount +import fr.iut.alldev.allin.ui.core.IconPosition + +@Composable +fun BetResultBottomSheetBetCardStats( + stake: Int, + winnings: Int, + odds: Float +) { + Column( + Modifier + .fillMaxWidth() + .background(AllInTheme.themeColors.background2) + .padding(horizontal = 19.dp, vertical = 11.dp), + verticalArrangement = Arrangement.spacedBy(12.dp) + ) { + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.SpaceBetween + ) { + Text( + text = stringResource(id = R.string.bet_result_stake), + style = AllInTheme.typography.sm2, + color = AllInTheme.themeColors.onMainSurface + ) + + AllInCoinCount( + amount = stake, + color = AllInTheme.colors.allInPurple, + textStyle = AllInTheme.typography.sm1, + position = IconPosition.TRAILING + ) + } + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.SpaceBetween + ) { + Text( + text = stringResource(id = R.string.bet_result_winnings), + style = AllInTheme.typography.sm2, + color = AllInTheme.colors.allInPurple + ) + AllInCoinCount( + amount = winnings, + textStyle = AllInTheme.typography.sm1, + brush = AllInTheme.colors.allInMainGradient, + position = IconPosition.TRAILING + ) + } + + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.SpaceBetween + ) { + Text( + text = stringResource(id = R.string.bet_result_odds), + style = AllInTheme.typography.sm2, + color = AllInTheme.themeColors.onBackground2 + ) + AllInCard( + radius = 8.dp, + backgroundBrush = AllInTheme.colors.allInMainGradient + ) { + Box(Modifier.padding(vertical = 4.dp, horizontal = 8.dp)) { + Text( + text = "$odds", + style = AllInTheme.typography.sm1, + color = AllInTheme.colors.white + ) + } + } + } + } +} + + +@Preview +@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +private fun BetResultBottomSheetBetCardStatsPreview() { + AllInTheme { + BetResultBottomSheetBetCardStats( + stake = 2446, + winnings = 6930, + odds = 2.3f + ) + } +} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetContentCongratulations.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetContentCongratulations.kt new file mode 100644 index 0000000..4af87f9 --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetBetContentCongratulations.kt @@ -0,0 +1,71 @@ +package fr.iut.alldev.allin.ui.betResult.components + +import androidx.compose.animation.core.RepeatMode +import androidx.compose.animation.core.animateFloat +import androidx.compose.animation.core.infiniteRepeatable +import androidx.compose.animation.core.rememberInfiniteTransition +import androidx.compose.animation.core.tween +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Row +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.runtime.getValue +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.draw.rotate +import androidx.compose.ui.draw.scale +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.text.font.FontStyle +import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import fr.iut.alldev.allin.R +import fr.iut.alldev.allin.theme.AllInTheme + +@Composable +fun BetResultBottomSheetContentCongratulations( + modifier: Modifier = Modifier, + username: String +) { + val infiniteTransition = rememberInfiniteTransition(label = "") + + val rotation by infiniteTransition.animateFloat( + initialValue = -11f, + targetValue = -5f, + animationSpec = infiniteRepeatable( + animation = tween(900), + repeatMode = RepeatMode.Reverse + ), label = "" + ) + + val scale by infiniteTransition.animateFloat( + initialValue = 1f, + targetValue = .9f, + animationSpec = infiniteRepeatable( + animation = tween(900), + repeatMode = RepeatMode.Reverse + ), label = "" + ) + + Row( + modifier = modifier + .rotate(rotation) + .scale(scale), + verticalAlignment = Alignment.Top, + horizontalArrangement = Arrangement.spacedBy(8.dp) + ) { + Text( + text= stringResource(id = R.string.bet_result_congratulations), + style = AllInTheme.typography.h1, + fontSize = 25.sp, + fontStyle = FontStyle.Italic, + color = AllInTheme.colors.white + ) + Text( + text = "${username.uppercase()} !", + style = AllInTheme.typography.h1, + fontSize = 30.sp, + fontStyle = FontStyle.Italic, + color = AllInTheme.colors.white + ) + } +} diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetContentCoinAmount.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetContentCoinAmount.kt new file mode 100644 index 0000000..bb9ed23 --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/components/BetResultBottomSheetContentCoinAmount.kt @@ -0,0 +1,79 @@ +package fr.iut.alldev.allin.ui.betResult.components + +import android.content.res.Configuration +import androidx.compose.foundation.border +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.offset +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.shape.RoundedCornerShape +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Alignment +import androidx.compose.ui.Modifier +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import fr.iut.alldev.allin.R +import fr.iut.alldev.allin.theme.AllInTheme +import fr.iut.alldev.allin.ui.core.AllInCoinCount +import fr.iut.alldev.allin.ui.core.IconPosition + +@Composable +fun BetResultBottomSheetContentCoinAmount( + modifier: Modifier = Modifier, + amount: Int +) { + Column( + verticalArrangement = Arrangement.spacedBy(14.dp), + horizontalAlignment = Alignment.CenterHorizontally, + ) { + Text( + text = stringResource(id = R.string.bet_result_you_win), + style = AllInTheme.typography.sm2, + color = AllInTheme.colors.white, + fontSize = 20.sp + ) + + Box( + modifier + .border( + width = 2.dp, + shape = RoundedCornerShape(100.dp), + color = AllInTheme.colors.white + ) + .padding(vertical = 22.dp, horizontal = 33.dp) + + ) { + AllInCoinCount( + amount = amount, + textStyle = AllInTheme.typography.h1, + position = IconPosition.TRAILING, + color = AllInTheme.colors.white, + size = 60, + modifier = Modifier + .align(Alignment.Center) + .offset(y = (-6).dp) + ) + AllInCoinCount( + amount = amount, + textStyle = AllInTheme.typography.h1, + position = IconPosition.TRAILING, + color = AllInTheme.colors.white.copy(alpha = .32f), + size = 60, + modifier = Modifier.align(Alignment.Center) + ) + } + } +} + +@Preview +@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +private fun BetResultBottomSheetContentCoinAmountPreview() { + AllInTheme { + BetResultBottomSheetContentCoinAmount(amount = 1572) + } +} diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt index 2c37b47..491cb19 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt @@ -8,9 +8,7 @@ import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.Color import fr.iut.alldev.allin.data.model.bet.Bet import fr.iut.alldev.allin.ui.betStatus.components.BetStatusBottomSheetBack -import fr.iut.alldev.allin.ui.betStatus.visitor.BetStatusBottomSheetDisplayBetVisitor import fr.iut.alldev.allin.ui.core.AllInBottomSheet -import fr.iut.alldev.allin.vo.bet.BetVO internal const val SHEET_HEIGHT = .85f @@ -22,9 +20,9 @@ fun BetStatusBottomSheet( state: SheetState, sheetVisibility: Boolean, sheetBackVisibility: Boolean, - bet: BetVO?, + bet: Bet?, onDismiss: ()->Unit, - visitor: BetStatusBottomSheetDisplayBetVisitor + displayBet: @Composable (Bet) -> Unit ) { AnimatedVisibility( visible = sheetBackVisibility, @@ -37,7 +35,7 @@ fun BetStatusBottomSheet( ) { bet?.let { BetStatusBottomSheetBack( - status = it.bet.betStatus + status = it.betStatus ) } } @@ -51,7 +49,9 @@ fun BetStatusBottomSheet( Column( Modifier.fillMaxHeight(SHEET_HEIGHT) ) { - bet?.Accept(visitor) + bet?.let { + displayBet(it) + } } } } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt index 8c88061..4ab56ae 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt @@ -1,6 +1,5 @@ package fr.iut.alldev.allin.ui.betStatus.components -import android.content.res.Configuration import androidx.compose.foundation.background import androidx.compose.foundation.layout.* import androidx.compose.material3.* @@ -9,7 +8,6 @@ import androidx.compose.runtime.rememberCoroutineScope import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.res.stringResource -import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.Dp import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp @@ -31,6 +29,7 @@ fun BetStatusParticipationBottomSheet( onDismiss: () -> Unit, state: SheetState, onParticipate: () -> Unit, + content: @Composable () -> Unit ) { val scope = rememberCoroutineScope() AllInBottomSheet( @@ -61,7 +60,7 @@ fun BetStatusParticipationBottomSheet( Spacer(modifier = Modifier.height(30.dp)) Text( text = betPhrase, - style = AllInTheme.typography.s, + style = AllInTheme.typography.p2, color = AllInTheme.themeColors.onMainSurface, modifier = Modifier.padding(horizontal = 18.dp) ) @@ -81,7 +80,7 @@ fun BetStatusParticipationBottomSheet( ) { Text( text = stringResource(id = R.string.Possible_winnings), - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, color = AllInTheme.themeColors.onBackground ) AllInCoinCount( @@ -89,6 +88,9 @@ fun BetStatusParticipationBottomSheet( color = AllInTheme.themeColors.onBackground ) } + Box(modifier = Modifier.fillMaxSize()) { + content() + } AllInButton( color = AllInTheme.colors.allInPurple, text = stringResource(id = R.string.Participate), @@ -103,23 +105,4 @@ fun BetStatusParticipationBottomSheet( } } } -} - - -@OptIn(ExperimentalMaterial3Api::class) -@Preview -@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) -@Composable -private fun BetStatusParticipationBottomSheetPreview() { - AllInTheme { - BetStatusParticipationBottomSheet( - sheetVisibility = true, - safeBottomPadding = 5.dp, - betPhrase = "Lorem Ipsum", - coinAmount = 125, - onDismiss = {}, - state = rememberModalBottomSheetState(), - onParticipate = {} - ) - } } \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusWinner.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusWinner.kt index 92da99d..e8292b7 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusWinner.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusWinner.kt @@ -15,6 +15,7 @@ import androidx.compose.runtime.Composable import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.Color +import androidx.compose.ui.graphics.vector.rememberVectorPainter import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.dp import fr.iut.alldev.allin.theme.AllInTheme @@ -41,7 +42,7 @@ fun BetStatusWinner( ) { AllInTextIcon( text = answer, - icon = Icons.Filled.EmojiEvents, + icon = rememberVectorPainter(image = Icons.Filled.EmojiEvents), color = color, size = 50, iconSize = 60, @@ -57,13 +58,13 @@ fun BetStatusWinner( ) AllInTextIcon( text = username, - icon = Icons.Filled.People, + icon = rememberVectorPainter(image = Icons.Filled.People), color = color, position = IconPosition.LEADING ) AllInTextIcon( text = "x" + String.format("%.1f", multiplier), - icon = Icons.Filled.EmojiEvents, + icon = rememberVectorPainter(image = Icons.Filled.EmojiEvents), color = color, position = IconPosition.LEADING ) diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoDetailsLine.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoDetailsLine.kt index acf8245..784b368 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoDetailsLine.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoDetailsLine.kt @@ -8,6 +8,7 @@ import androidx.compose.runtime.Composable import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.painter.Painter import androidx.compose.ui.graphics.vector.ImageVector +import androidx.compose.ui.graphics.vector.rememberVectorPainter import androidx.compose.ui.tooling.preview.Preview import fr.iut.alldev.allin.theme.AllInTheme import fr.iut.alldev.allin.ui.core.AllInTextIcon @@ -26,7 +27,7 @@ fun YesNoDetailsLine( AllInTextIcon( text = yesText, color = AllInTheme.colors.allInBlue, - icon = icon, + icon = rememberVectorPainter(image = icon), position = IconPosition.LEADING, size = 10, iconSize = 15 @@ -34,7 +35,7 @@ fun YesNoDetailsLine( AllInTextIcon( text = noText, color = AllInTheme.colors.allInBarPink, - icon = icon, + icon = rememberVectorPainter(image = icon), position = IconPosition.TRAILING, size = 10, iconSize = 15 diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoStarBar.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoStarBar.kt index 5366b1a..5abafbd 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoStarBar.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoStarBar.kt @@ -45,7 +45,7 @@ fun YesNoStatBar( ) { Text( text = yesPercentage.toPercentageString(), - style = AllInTheme.typography.h3, + style = AllInTheme.typography.sm1, color = AllInTheme.colors.allInBarPurple ) } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/visitor/BetStatusBottomSheetDisplayBetVisitor.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/vo/BetStatusBottomSheetBetDisplayer.kt similarity index 72% rename from src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/visitor/BetStatusBottomSheetDisplayBetVisitor.kt rename to src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/vo/BetStatusBottomSheetBetDisplayer.kt index 62c1fd0..00c80e4 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/visitor/BetStatusBottomSheetDisplayBetVisitor.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/vo/BetStatusBottomSheetBetDisplayer.kt @@ -1,4 +1,4 @@ -package fr.iut.alldev.allin.ui.betStatus.visitor +package fr.iut.alldev.allin.ui.betStatus.vo import android.content.res.Configuration import androidx.compose.foundation.background @@ -16,12 +16,14 @@ import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.res.stringResource import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.tooling.preview.PreviewParameter import androidx.compose.ui.unit.dp import fr.iut.alldev.allin.R import fr.iut.alldev.allin.data.ext.formatToMediumDateNoYear import fr.iut.alldev.allin.data.ext.formatToTime -import fr.iut.alldev.allin.data.model.bet.BetFinishedStatus +import fr.iut.alldev.allin.data.model.bet.Bet import fr.iut.alldev.allin.data.model.bet.BetStatus +import fr.iut.alldev.allin.data.model.bet.CustomBet import fr.iut.alldev.allin.data.model.bet.MatchBet import fr.iut.alldev.allin.data.model.bet.YesNoBet import fr.iut.alldev.allin.ext.getDateEndLabelId @@ -35,38 +37,32 @@ import fr.iut.alldev.allin.ui.core.AllInDetailsDrawer import fr.iut.alldev.allin.ui.core.RainbowButton import fr.iut.alldev.allin.ui.core.bet.BetDateTimeRow import fr.iut.alldev.allin.ui.core.bet.BetTitleHeader -import fr.iut.alldev.allin.vo.bet.factory.toBetVO -import fr.iut.alldev.allin.vo.bet.visitor.DisplayBetVisitor -import java.time.ZonedDateTime +import fr.iut.alldev.allin.ui.preview.BetWithStatusPreviewProvider +import fr.iut.alldev.allin.vo.bet.BetDisplayer -class BetStatusBottomSheetDisplayBetVisitor( +class BetStatusBottomSheetBetDisplayer( val userCoinAmount: MutableIntState, val onParticipate: (Int) -> Unit, -) : DisplayBetVisitor { - +) : BetDisplayer { val participateBottomSheetVisibility = mutableStateOf(false) val paddingValues = mutableStateOf(PaddingValues()) @OptIn(ExperimentalMaterial3Api::class) @Composable - override fun VisitYesNoBet(b: YesNoBet) { + override fun DisplayYesNoBet(b: YesNoBet) { val (participateSheetVisibility, setParticipateSheetVisibility) = remember { this.participateBottomSheetVisibility } - val safeBottomPadding = paddingValues.value.calculateBottomPadding() - Box( - Modifier - .padding(bottom = safeBottomPadding) - ) { + Box(Modifier.padding(bottom = safeBottomPadding)) { Column { Column(Modifier.padding(horizontal = 20.dp)) { BetTitleHeader( title = b.phrase, category = b.theme, - creator = "Lucas" /*TODO : Creator*/, + creator = b.creator, modifier = Modifier.fillMaxWidth() ) Spacer(modifier = Modifier.height(20.dp)) @@ -152,85 +148,37 @@ class BetStatusBottomSheetDisplayBetVisitor( betPhrase = b.phrase, coinAmount = userCoinAmount.intValue, onDismiss = { setParticipateSheetVisibility(false) }, - state = rememberModalBottomSheetState() + state = rememberModalBottomSheetState(), + onParticipate = { + onParticipate(100) + } ) { - onParticipate(100) + } } @Composable - override fun VisitMatchBet(b: MatchBet) { + override fun DisplayMatchBet(b: MatchBet) { Text("This is a MATCH BET") } -} - -@Preview -@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) -@Composable -private fun YesNoBetPreview() { - AllInTheme { - val coins = remember { mutableIntStateOf(100) } - YesNoBet( - theme = "Theme", - phrase = "Phrase", - endRegisterDate = ZonedDateTime.now(), - endBetDate = ZonedDateTime.now(), - isPublic = true, - betStatus = BetStatus.InProgress, - creator = "creator" - ).toBetVO()?.Accept( - BetStatusBottomSheetDisplayBetVisitor( - userCoinAmount = coins, - onParticipate = {} - ) - ) - } -} -@Preview -@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) -@Composable -private fun YesNoBetFinishedPreview() { - AllInTheme { - val coins = remember { mutableIntStateOf(100) } - YesNoBet( - theme = "Theme", - phrase = "Phrase", - endRegisterDate = ZonedDateTime.now(), - endBetDate = ZonedDateTime.now(), - isPublic = true, - betStatus = BetStatus.Finished(BetFinishedStatus.WON), - creator = "creator" - ).toBetVO()?.Accept( - BetStatusBottomSheetDisplayBetVisitor( - userCoinAmount = coins, - onParticipate = {} - ) - ) + @Composable + override fun DisplayCustomBet(b: CustomBet) { + Text("This is a CUSTOM BET") } } @Preview @Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) @Composable -private fun MatchBetPreview() { +private fun BetStatusBottomSheetPreview( + @PreviewParameter(BetWithStatusPreviewProvider::class) bet: Bet +) { AllInTheme { val coins = remember { mutableIntStateOf(100) } - MatchBet( - theme = "Theme", - phrase = "Phrase", - endRegisterDate = ZonedDateTime.now(), - endBetDate = ZonedDateTime.now(), - isPublic = true, - betStatus = BetStatus.InProgress, - nameTeam1 = "Team 1", - nameTeam2 = "Team 2", - creator = "creator" - ).toBetVO()?.Accept( - BetStatusBottomSheetDisplayBetVisitor( - userCoinAmount = coins, - onParticipate = {} - ) - ) + BetStatusBottomSheetBetDisplayer( + userCoinAmount = coins, + onParticipate = {} + ).DisplayBet(bet) } } \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInAlertDialog.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInAlertDialog.kt index 8bae7c6..f2ffd39 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInAlertDialog.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInAlertDialog.kt @@ -32,7 +32,7 @@ fun AllInAlertDialog( text = { Text( text = text, - style = AllInTheme.typography.r + style = AllInTheme.typography.p1 ) }, confirmButton = { diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInBottomSheet.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInBottomSheet.kt index 43f29ef..07954b7 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInBottomSheet.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInBottomSheet.kt @@ -18,6 +18,7 @@ fun AllInBottomSheet( state: SheetState, scrimColor: Color = BottomSheetDefaults.ScrimColor, containerColor: Color = AllInTheme.themeColors.background, + dragHandle: (@Composable ()->Unit)? = { BottomSheetDefaults.DragHandle() }, content: @Composable ColumnScope.()->Unit ) { val localDensity = LocalDensity.current @@ -38,6 +39,7 @@ fun AllInBottomSheet( bottom = 0, ) }, + dragHandle = dragHandle, content = content ) } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInChip.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInChip.kt index 63846f7..fb5dbdf 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInChip.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInChip.kt @@ -44,7 +44,7 @@ fun AllInChip( .padding(vertical = 8.dp, horizontal = 22.dp) .alpha(if (isSelected) 0f else 1f), textAlign = TextAlign.Center, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, color = AllInTheme.themeColors.onBackground2 ) if (isSelected) { diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInCoinCount.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInCoinCount.kt index 1613a6a..99c10a0 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInCoinCount.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInCoinCount.kt @@ -3,7 +3,9 @@ package fr.iut.alldev.allin.ui.core import android.content.res.Configuration import androidx.compose.runtime.Composable import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.Brush import androidx.compose.ui.graphics.Color +import androidx.compose.ui.text.TextStyle import androidx.compose.ui.tooling.preview.Preview import fr.iut.alldev.allin.theme.AllInTheme @@ -11,14 +13,20 @@ import fr.iut.alldev.allin.theme.AllInTheme fun AllInCoinCount( modifier: Modifier = Modifier, amount: Int, - color: Color, - position: IconPosition = IconPosition.TRAILING, + color: Color? = null, + brush: Brush?= null, + size: Int = 15, + textStyle: TextStyle = AllInTheme.typography.h1, + position: IconPosition = IconPosition.TRAILING ) { AllInTextIcon( text = amount.toString(), icon = AllInTheme.icons.allCoins(), - color = color, + color = color ?: Color.Black, + brush = brush, position = position, + textStyle = textStyle, + size = size, modifier = modifier ) } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInDatePicker.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInDatePicker.kt index 9ac4a4e..6b5a41d 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInDatePicker.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInDatePicker.kt @@ -51,7 +51,7 @@ fun AllInDatePicker( Text( text = stringResource(id = R.string.Cancel), color = AllInTheme.themeColors.onBackground2, - style = AllInTheme.typography.h3 + style = AllInTheme.typography.sm1 ) } }, diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInDetailsDrawer.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInDetailsDrawer.kt index 4a38160..22def8f 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInDetailsDrawer.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInDetailsDrawer.kt @@ -58,7 +58,7 @@ fun AllInDetailsDrawer( ) { Text( text = text, - style = AllInTheme.typography.s, + style = AllInTheme.typography.p2, color = textColor, fontSize = 15.sp ) diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInErrorLine.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInErrorLine.kt index 4565cff..611c4b2 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInErrorLine.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInErrorLine.kt @@ -12,7 +12,7 @@ import fr.iut.alldev.allin.theme.AllInTheme fun AllInErrorLine(text: String) { Text( text = text, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, color = Color.Red, fontSize = 10.sp, overflow = TextOverflow.Ellipsis diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInRetractableCard.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInRetractableCard.kt index e023a85..8b552e6 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInRetractableCard.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInRetractableCard.kt @@ -64,7 +64,7 @@ fun AllInRetractableCard( fontStyle = AllInTheme.typography.h2.fontStyle ), color = AllInTheme.themeColors.onBackground2, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, fontSize = 16.sp, modifier = Modifier.weight(1f) ) diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInSectionButton.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInSectionButton.kt index 01113fc..8f8ef77 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInSectionButton.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInSectionButton.kt @@ -20,14 +20,14 @@ fun AllInSectionButton( onClick: (Int) -> Unit, ) { val style = if (isSelected) { - AllInTheme.typography.h3.copy( + AllInTheme.typography.sm1.copy( color = AllInTheme.themeColors.onMainSurface, fontSize = 15.sp, textAlign = TextAlign.Center, fontWeight = FontWeight.ExtraBold ) } else { - AllInTheme.typography.h3.copy( + AllInTheme.typography.sm1.copy( color = AllInTheme.themeColors.onBackground2, fontSize = 15.sp, textAlign = TextAlign.Center, diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextField.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextField.kt index a528297..9382045 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextField.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextField.kt @@ -90,7 +90,7 @@ fun AllInTextField( Text( text = placeholder, fontSize = placeholderFontSize, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, color = placeholderColor, maxLines = if (multiLine) 3 else 1, overflow = TextOverflow.Ellipsis @@ -105,7 +105,7 @@ fun AllInTextField( ) } }, - textStyle = AllInTheme.typography.r, + textStyle = AllInTheme.typography.p1, enabled = enabled, keyboardOptions = KeyboardOptions(keyboardType = keyboardType, imeAction = imeAction), keyboardActions = keyboardActions, diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextIcon.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextIcon.kt index b12004e..3827926 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextIcon.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextIcon.kt @@ -6,16 +6,17 @@ import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.size import androidx.compose.material.icons.Icons import androidx.compose.material.icons.filled.Fireplace -import androidx.compose.material3.Icon import androidx.compose.material3.Text import androidx.compose.runtime.Composable import androidx.compose.runtime.CompositionLocalProvider import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.Brush import androidx.compose.ui.graphics.Color import androidx.compose.ui.graphics.painter.Painter -import androidx.compose.ui.graphics.vector.ImageVector +import androidx.compose.ui.graphics.vector.rememberVectorPainter import androidx.compose.ui.platform.LocalLayoutDirection +import androidx.compose.ui.text.TextStyle import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.LayoutDirection import androidx.compose.ui.unit.dp @@ -34,6 +35,8 @@ fun AllInTextIcon( text: String, icon: Painter, color: Color, + brush: Brush? = null, + textStyle: TextStyle = AllInTheme.typography.h1, position: IconPosition = IconPosition.TRAILING, size: Int = 15, iconSize: Int = size, @@ -52,54 +55,15 @@ fun AllInTextIcon( Text( text = text, color = color, - style = AllInTheme.typography.h1, + style = brush?.let { textStyle.copy(brush = it) } ?: textStyle, fontSize = size.sp ) Icon( painter = icon, contentDescription = null, modifier = Modifier.size(iconSize.dp), - tint = color - ) - } - } - } -} - - -@Composable -fun AllInTextIcon( - modifier: Modifier = Modifier, - text: String, - icon: ImageVector, - color: Color, - position: IconPosition = IconPosition.TRAILING, - size: Int = 15, - iconSize: Int = size, -) { - val direction = - if (position == IconPosition.LEADING) LayoutDirection.Rtl - else LayoutDirection.Ltr - Box(modifier) { - CompositionLocalProvider( - LocalLayoutDirection provides direction - ) { - Row( - modifier = modifier, - verticalAlignment = Alignment.CenterVertically, - horizontalArrangement = Arrangement.spacedBy(7.dp) - ) { - Text( - text = text, - color = color, - style = AllInTheme.typography.h1, - fontSize = size.sp - ) - Icon( - imageVector = icon, - contentDescription = null, - modifier = Modifier.size(iconSize.dp), - tint = color + tint = color, + brush = brush ) } } @@ -112,7 +76,7 @@ private fun AllInTextIconPreview() { AllInTheme { AllInTextIcon( text = "value", - icon = Icons.Default.Fireplace, + icon = rememberVectorPainter(image = Icons.Default.Fireplace), color = AllInTheme.colors.allInBlue ) } @@ -126,6 +90,7 @@ private fun AllInTextIconReversePreview() { text = "value", icon = AllInTheme.icons.allCoins(), color = AllInTheme.colors.allInBlue, + brush = AllInTheme.colors.allInMainGradient, position = IconPosition.LEADING ) } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTimePicker.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTimePicker.kt index 5ddcdc5..b78e0d2 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTimePicker.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTimePicker.kt @@ -46,7 +46,7 @@ fun AllInTimePicker( Text( text = stringResource(id = R.string.Cancel), color = AllInTheme.themeColors.onBackground2, - style = AllInTheme.typography.h3 + style = AllInTheme.typography.sm1 ) } }, diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTooltip.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTooltip.kt index bf5123a..5254aa6 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTooltip.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTooltip.kt @@ -31,7 +31,7 @@ fun AllInTooltip( Text( text = text, color = AllInTheme.colors.allInLightGrey200, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, fontSize = 12.sp ) } @@ -121,7 +121,7 @@ private fun AllInTooltipPreview() { Text( text = "Généralement une question qui sera répondu par les utilisateurs.", color = AllInTheme.colors.allInLightGrey200, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, fontSize = 10.sp ) }) diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/Icon.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/Icon.kt new file mode 100644 index 0000000..6ccb149 --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/Icon.kt @@ -0,0 +1,38 @@ +package fr.iut.alldev.allin.ui.core + +import androidx.compose.material3.Icon +import androidx.compose.material3.LocalContentColor +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.draw.drawWithCache +import androidx.compose.ui.graphics.BlendMode +import androidx.compose.ui.graphics.Brush +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.graphics.CompositingStrategy +import androidx.compose.ui.graphics.graphicsLayer +import androidx.compose.ui.graphics.painter.Painter + +@Composable +fun Icon( + painter: Painter, + contentDescription: String?, + modifier: Modifier = Modifier, + tint: Color = LocalContentColor.current, + brush: Brush? = null, +) { + Icon( + painter = painter, + contentDescription = contentDescription, + modifier = brush?.let { + modifier + .graphicsLayer { compositingStrategy = CompositingStrategy.Offscreen } + .drawWithCache { + onDrawWithContent { + drawContent() + drawRect(brush, blendMode = BlendMode.SrcAtop) + } + } + } ?: modifier, + tint = tint + ) +} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetCard.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetCard.kt new file mode 100644 index 0000000..a7e6613 --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetCard.kt @@ -0,0 +1,76 @@ +package fr.iut.alldev.allin.ui.core.bet + +import android.content.res.Configuration +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.material3.HorizontalDivider +import androidx.compose.material3.Text +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.dp +import fr.iut.alldev.allin.data.model.bet.BetStatus +import fr.iut.alldev.allin.ext.getDateStartLabelId +import fr.iut.alldev.allin.theme.AllInTheme +import fr.iut.alldev.allin.ui.core.AllInCard + +@Composable +fun BetCard( + modifier: Modifier = Modifier, + title: String, + creator: String, + category: String, + date: String, + time: String, + status: BetStatus, + content: @Composable () -> Unit +) { + AllInCard( + modifier = modifier.fillMaxWidth(), + radius = 16.dp + ) { + Column( + Modifier.padding(horizontal = 19.dp, vertical = 11.dp) + ) { + BetTitleHeader( + title = title, + category = category, + creator = creator, + modifier = Modifier.fillMaxWidth() + ) + Spacer(modifier = Modifier.height(11.dp)) + BetDateTimeRow( + label = stringResource(id = status.getDateStartLabelId()), + date = date, + time = time + ) + } + HorizontalDivider( + thickness = 1.dp, + color = AllInTheme.themeColors.border + ) + content() + } +} + +@Preview +@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +private fun BetCardPreview() { + AllInTheme { + BetCard( + creator = "Creator", + category = "Category", + title = "Title", + date = "Date", + time = "Time", + status = BetStatus.Waiting + ){ + Text("Content") + } + } +} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetDateTimeChip.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetDateTimeChip.kt index b6e9bea..256d170 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetDateTimeChip.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetDateTimeChip.kt @@ -29,7 +29,7 @@ fun BetDateTimeChip( Text( text = text, modifier = Modifier.padding(vertical = 8.dp, horizontal = 16.dp), - style = AllInTheme.typography.h3, + style = AllInTheme.typography.sm1, textAlign = TextAlign.Center, color = AllInTheme.colors.allInPurple ) diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetDateTimeRow.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetDateTimeRow.kt index e8d99d5..1dccea0 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetDateTimeRow.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetDateTimeRow.kt @@ -27,7 +27,7 @@ fun BetDateTimeRow( Text( text = label, fontSize = 15.sp, - style = AllInTheme.typography.m, + style = AllInTheme.typography.sm2, color = AllInTheme.themeColors.onBackground2 ) BetDateTimeChip(date) diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetTitleHeader.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetTitleHeader.kt index a732e02..41a7743 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetTitleHeader.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/bet/BetTitleHeader.kt @@ -38,7 +38,7 @@ fun BetTitleHeader( color = AllInTheme.themeColors.onMainSurface ), fontSize = 12.sp, - style = AllInTheme.typography.s, + style = AllInTheme.typography.p2, color = AllInTheme.themeColors.onBackground2 ) } @@ -47,7 +47,7 @@ fun BetTitleHeader( text = category, fontSize = 15.sp, color = AllInTheme.themeColors.onBackground2, - style = AllInTheme.typography.m + style = AllInTheme.typography.sm2 ) Text( text = title, diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/snackbar/AllInSnackBar.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/snackbar/AllInSnackBar.kt index d9b2129..5e69ace 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/snackbar/AllInSnackBar.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/snackbar/AllInSnackBar.kt @@ -105,7 +105,7 @@ fun AllInSnackbarContent( Text( text = text, color = contentColor, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, overflow = TextOverflow.Ellipsis, maxLines = 5, modifier = Modifier.weight(1f) diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/login/LoginScreen.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/login/LoginScreen.kt index dea639f..1b9bd80 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/login/LoginScreen.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/login/LoginScreen.kt @@ -84,7 +84,7 @@ fun LoginScreen( modifier = Modifier.fillMaxWidth(), text = stringResource(id = R.string.Login_title), color = AllInTheme.themeColors.onMainSurface, - style = AllInTheme.typography.h3, + style = AllInTheme.typography.sm1, textAlign = TextAlign.Center, fontSize = 40.sp ) @@ -93,7 +93,7 @@ fun LoginScreen( modifier = Modifier.fillMaxWidth(), text = stringResource(id = R.string.Login_subtitle), color = AllInTheme.themeColors.onMainSurface, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, textAlign = TextAlign.Center, fontSize = 23.sp ) @@ -122,7 +122,7 @@ fun LoginScreen( } ClickableText( text = AnnotatedString(stringResource(id = R.string.forgot_password)), - style = AllInTheme.typography.m.copy( + style = AllInTheme.typography.sm2.copy( color = AllInTheme.themeColors.onMainSurface, fontSize = 15.sp, ), @@ -156,12 +156,12 @@ fun LoginScreen( text = stringResource(id = R.string.no_account), color = AllInTheme.themeColors.onMainSurface, fontSize = 15.sp, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, modifier = Modifier.padding(end = 5.dp) ) ClickableText( text = AnnotatedString(stringResource(id = R.string.Register)), - style = AllInTheme.typography.r.copy( + style = AllInTheme.typography.p1.copy( color = AllInTheme.colors.allInPurple, fontSize = 15.sp, fontWeight = FontWeight.Bold diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt index c55cad1..1ba9b8f 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt @@ -11,8 +11,9 @@ import androidx.hilt.navigation.compose.hiltViewModel import androidx.navigation.NavHostController import androidx.navigation.compose.rememberNavController import fr.iut.alldev.allin.theme.AllInTheme +import fr.iut.alldev.allin.ui.betResult.BetResultBottomSheet import fr.iut.alldev.allin.ui.betStatus.BetStatusBottomSheet -import fr.iut.alldev.allin.ui.betStatus.visitor.BetStatusBottomSheetDisplayBetVisitor +import fr.iut.alldev.allin.ui.betStatus.vo.BetStatusBottomSheetBetDisplayer import fr.iut.alldev.allin.ui.core.AllInLoading import fr.iut.alldev.allin.ui.core.snackbar.AllInSnackbarVisualsImpl import fr.iut.alldev.allin.ui.main.components.AllInScaffold @@ -21,7 +22,6 @@ import fr.iut.alldev.allin.ui.navigation.Routes import fr.iut.alldev.allin.ui.navigation.TopLevelDestination import fr.iut.alldev.allin.ui.navigation.drawer.AllInDrawer import fr.iut.alldev.allin.ui.navigation.popUpTo -import fr.iut.alldev.allin.vo.bet.factory.toBetVO import kotlinx.coroutines.launch private val topLevelDestinations = listOf( @@ -68,10 +68,12 @@ fun MainScreen( var loading by remember { mainViewModel.loading } val currentUser = remember { mainViewModel.currentUserState } val (selectedBet, setSelectedBet) = remember { mainViewModel.selectedBet } + val (wonBet, setWonBet) = remember { mainViewModel.wonBet } val (statusVisibility, sheetBackVisibility, setStatusVisibility) = rememberBetStatusVisibilities() + val (displayResult, setDisplayResult ) = remember{ mutableStateOf(true) } - val betStatusDisplayVisitor = remember { - BetStatusBottomSheetDisplayBetVisitor( + val betStatusDisplayer = remember { + BetStatusBottomSheetBetDisplayer( userCoinAmount = currentUser.userCoins, onParticipate = { mainViewModel.participateToBet(it) @@ -100,7 +102,7 @@ fun MainScreen( } } - val bottomSheetState = rememberModalBottomSheetState( + val statusBottomSheetState = rememberModalBottomSheetState( skipPartiallyExpanded = true, confirmValueChange = { if (it == SheetValue.Hidden) { @@ -110,6 +112,10 @@ fun MainScreen( } ) + val resultBottomSheetState = rememberModalBottomSheetState( + skipPartiallyExpanded = true + ) + AllInDrawer( drawerState = drawerState, destinations = topLevelDestinations, @@ -133,7 +139,7 @@ fun MainScreen( snackbarHostState = snackbarHostState ) { LaunchedEffect(key1 = it) { - betStatusDisplayVisitor.paddingValues.value = it + betStatusDisplayer.paddingValues.value = it } Column( modifier = Modifier @@ -146,7 +152,7 @@ fun MainScreen( navController = navController, selectBet = { bet, participate -> setSelectedBet(bet) - betStatusDisplayVisitor.participateBottomSheetVisibility.value = participate + betStatusDisplayer.participateBottomSheetVisibility.value = participate setStatusVisibility(true) }, setLoading = { loading = it }, @@ -156,15 +162,29 @@ fun MainScreen( } } + wonBet?.let { + BetResultBottomSheet( + state = resultBottomSheetState, + sheetVisibility = displayResult, + onDismiss = { setDisplayResult(false) }, + bet = wonBet, + username = currentUser.user.username, + coinAmount = 1630, + stake = 1630, + winnings = 1630, + odds = 3.62f + ) + } + BetStatusBottomSheet( - state = bottomSheetState, + state = statusBottomSheetState, sheetVisibility = statusVisibility.value, sheetBackVisibility = sheetBackVisibility.value, onDismiss = { setStatusVisibility(false) }, - bet = selectedBet?.toBetVO(), - visitor = betStatusDisplayVisitor + bet = selectedBet, + displayBet = { betStatusDisplayer.DisplayBet(it) } ) AllInLoading(visible = loading) BackHandler( diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt index 33d7f3e..8287d8c 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt @@ -8,12 +8,16 @@ import androidx.lifecycle.viewModelScope import dagger.hilt.android.lifecycle.HiltViewModel import fr.iut.alldev.allin.data.model.User import fr.iut.alldev.allin.data.model.bet.Bet +import fr.iut.alldev.allin.data.model.bet.BetFinishedStatus +import fr.iut.alldev.allin.data.model.bet.BetStatus +import fr.iut.alldev.allin.data.model.bet.YesNoBet import fr.iut.alldev.allin.di.AllInCurrentUser import fr.iut.alldev.allin.keystore.AllInKeystoreManager import fr.iut.alldev.allin.ui.core.snackbar.SnackbarType import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch import kotlinx.coroutines.withContext +import java.time.ZonedDateTime import javax.inject.Inject class UserState(val user: User) { @@ -30,6 +34,17 @@ class MainViewModel @Inject constructor( val currentUserState = UserState(currentUser) val selectedBet = mutableStateOf(null) + val wonBet = mutableStateOf( + YesNoBet( + theme = "Theme", + phrase = "Phrase", + endRegisterDate = ZonedDateTime.now(), + endBetDate = ZonedDateTime.now(), + isPublic = true, + betStatus = BetStatus.Finished(BetFinishedStatus.WON), + creator = "creator" + ) + ) val snackbarContent: MutableState by lazy { mutableStateOf(null) } fun putSnackbarContent(content: SnackbarContent) { diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/AllInDrawer.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/AllInDrawer.kt index a86410f..c9442ae 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/AllInDrawer.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/AllInDrawer.kt @@ -74,7 +74,7 @@ fun AllInDrawer( ) { Text( text = stringResource(id = R.string.Logout), - style = AllInTheme.typography.h3, + style = AllInTheme.typography.sm1, color = AllInTheme.colors.allInDarkGrey50, fontSize = 16.sp ) diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/components/DrawerCell.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/components/DrawerCell.kt index 2d40781..392d9ce 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/components/DrawerCell.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/components/DrawerCell.kt @@ -56,7 +56,7 @@ fun DrawerCell( ) Text( text = subtitle, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, fontSize = 9.sp, color = AllInTheme.colors.allInLightGrey300, ) diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/components/DrawerHeaderStat.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/components/DrawerHeaderStat.kt index 4d302c6..33a5bf3 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/components/DrawerHeaderStat.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/navigation/drawer/components/DrawerHeaderStat.kt @@ -23,7 +23,7 @@ fun DrawerHeaderStat( Text( text = label, color = AllInTheme.colors.allInLightGrey300, - style = AllInTheme.typography.r + style = AllInTheme.typography.p1 ) } } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt new file mode 100644 index 0000000..304f569 --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt @@ -0,0 +1,51 @@ +package fr.iut.alldev.allin.ui.preview + +import androidx.compose.ui.tooling.preview.PreviewParameterProvider +import fr.iut.alldev.allin.data.model.bet.Bet +import fr.iut.alldev.allin.data.model.bet.BetFinishedStatus +import fr.iut.alldev.allin.data.model.bet.BetStatus +import fr.iut.alldev.allin.data.model.bet.CustomBet +import fr.iut.alldev.allin.data.model.bet.MatchBet +import fr.iut.alldev.allin.data.model.bet.YesNoBet +import java.time.ZonedDateTime + +class BetPreviewProvider: PreviewParameterProvider { + override val values = sequenceOf( + YesNoBet( + theme = "Theme", + phrase = "Phrase", + endRegisterDate = ZonedDateTime.now(), + endBetDate = ZonedDateTime.now(), + isPublic = true, + betStatus = BetStatus.Finished(BetFinishedStatus.WON), + creator = "creator" + ), + MatchBet( + theme = "Theme", + phrase = "Phrase", + endRegisterDate = ZonedDateTime.now(), + endBetDate = ZonedDateTime.now(), + isPublic = true, + betStatus = BetStatus.Finished(BetFinishedStatus.WON), + creator = "creator", + nameTeam1 = "The Monarchs", + nameTeam2 = "Climate Change" + ), + CustomBet( + theme = "Theme", + phrase = "Phrase", + endRegisterDate = ZonedDateTime.now(), + endBetDate = ZonedDateTime.now(), + isPublic = true, + betStatus = BetStatus.Finished(BetFinishedStatus.WON), + creator = "creator", + possibleAnswers = setOf( + "Answer 1", + "Answer 2", + "Answer 3", + "Answer 4" + ) + + ), + ) +} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetStatus.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetStatus.kt deleted file mode 100644 index f0de24e..0000000 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetStatus.kt +++ /dev/null @@ -1,14 +0,0 @@ -package fr.iut.alldev.allin.ui.preview - -import androidx.compose.ui.tooling.preview.PreviewParameterProvider -import fr.iut.alldev.allin.data.model.bet.BetFinishedStatus -import fr.iut.alldev.allin.data.model.bet.BetStatus - -class BetStatusPreviewProvider: PreviewParameterProvider { - override val values = sequenceOf( - BetStatus.InProgress, - BetStatus.Waiting, - BetStatus.Finished(BetFinishedStatus.WON), - BetStatus.Finished(BetFinishedStatus.LOST) - ) -} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetStatusPreviewProvider.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetStatusPreviewProvider.kt new file mode 100644 index 0000000..ccb3cd8 --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetStatusPreviewProvider.kt @@ -0,0 +1,8 @@ +package fr.iut.alldev.allin.ui.preview + +import androidx.compose.ui.tooling.preview.PreviewParameterProvider +import fr.iut.alldev.allin.data.model.bet.BetStatus + +class BetStatusPreviewProvider : PreviewParameterProvider { + override val values = BetStatus.entries +} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt new file mode 100644 index 0000000..becf11a --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt @@ -0,0 +1,53 @@ +package fr.iut.alldev.allin.ui.preview + +import androidx.compose.ui.tooling.preview.PreviewParameterProvider +import fr.iut.alldev.allin.data.model.bet.Bet +import fr.iut.alldev.allin.data.model.bet.BetStatus +import fr.iut.alldev.allin.data.model.bet.CustomBet +import fr.iut.alldev.allin.data.model.bet.MatchBet +import fr.iut.alldev.allin.data.model.bet.YesNoBet +import java.time.ZonedDateTime + + +class BetWithStatusPreviewProvider : PreviewParameterProvider { + override val values = BetStatus.entries.flatMap { status -> + sequenceOf( + YesNoBet( + theme = "Theme", + phrase = "Phrase", + endRegisterDate = ZonedDateTime.now(), + endBetDate = ZonedDateTime.now(), + isPublic = true, + betStatus = status, + creator = "creator" + ), + MatchBet( + theme = "Theme", + phrase = "Phrase", + endRegisterDate = ZonedDateTime.now(), + endBetDate = ZonedDateTime.now(), + isPublic = true, + betStatus = status, + creator = "creator", + nameTeam1 = "The Monarchs", + nameTeam2 = "Climate Change" + ), + CustomBet( + theme = "Theme", + phrase = "Phrase", + endRegisterDate = ZonedDateTime.now(), + endBetDate = ZonedDateTime.now(), + isPublic = true, + betStatus = status, + creator = "creator", + possibleAnswers = setOf( + "Answer 1", + "Answer 2", + "Answer 3", + "Answer 4" + ) + + ) + ) + } +} diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/register/RegisterScreen.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/register/RegisterScreen.kt index 35d3258..8a5f27b 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/register/RegisterScreen.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/register/RegisterScreen.kt @@ -89,7 +89,7 @@ fun RegisterScreen( modifier = Modifier.fillMaxWidth(), text = stringResource(id = R.string.Hello_x, username), color = AllInTheme.themeColors.onMainSurface, - style = AllInTheme.typography.h3, + style = AllInTheme.typography.sm1, textAlign = TextAlign.Center, fontSize = 40.sp, overflow = TextOverflow.Ellipsis, @@ -99,7 +99,7 @@ fun RegisterScreen( modifier = Modifier.fillMaxWidth(), text = stringResource(id = R.string.Register_title), color = AllInTheme.themeColors.onMainSurface, - style = AllInTheme.typography.h3, + style = AllInTheme.typography.sm1, textAlign = TextAlign.Center, fontSize = 40.sp ) @@ -108,7 +108,7 @@ fun RegisterScreen( modifier = Modifier.fillMaxWidth(), text = stringResource(id = R.string.Register_subtitle), color = AllInTheme.themeColors.onMainSurface, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, textAlign = TextAlign.Center, fontSize = 23.sp ) @@ -184,12 +184,12 @@ fun RegisterScreen( text = stringResource(id = R.string.already_have_account), color = AllInTheme.themeColors.onMainSurface, fontSize = 15.sp, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, modifier = Modifier.padding(end = 5.dp) ) ClickableText( text = AnnotatedString(stringResource(id = R.string.Login)), - style = AllInTheme.typography.r.copy( + style = AllInTheme.typography.p1.copy( color = AllInTheme.colors.allInPurple, fontSize = 15.sp, fontWeight = FontWeight.Bold diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/welcome/WelcomeScreen.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/welcome/WelcomeScreen.kt index 99f3ae4..c805f3c 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/welcome/WelcomeScreen.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/welcome/WelcomeScreen.kt @@ -88,7 +88,7 @@ fun WelcomeScreen( text = stringResource(id = R.string.welcome_subtitle), color = AllInTheme.themeColors.onBackground, fontSize = 15.sp, - style = AllInTheme.typography.r + style = AllInTheme.typography.p1 ) Spacer(modifier = Modifier.height(78.dp)) AllInButton( @@ -106,12 +106,12 @@ fun WelcomeScreen( text = stringResource(id = R.string.already_have_account), color = AllInTheme.themeColors.tint1, fontSize = 15.sp, - style = AllInTheme.typography.r, + style = AllInTheme.typography.p1, modifier = Modifier.padding(end = 5.dp) ) ClickableText( text = AnnotatedString(stringResource(id = R.string.Login)), - style = AllInTheme.typography.r.copy( + style = AllInTheme.typography.p1.copy( color = AllInTheme.themeColors.tint1, fontSize = 15.sp, fontWeight = FontWeight.Bold diff --git a/src/app/src/main/java/fr/iut/alldev/allin/vo/ViewObject.kt b/src/app/src/main/java/fr/iut/alldev/allin/vo/ViewObject.kt deleted file mode 100644 index ebd8358..0000000 --- a/src/app/src/main/java/fr/iut/alldev/allin/vo/ViewObject.kt +++ /dev/null @@ -1,8 +0,0 @@ -package fr.iut.alldev.allin.vo - -import androidx.compose.runtime.Composable - -interface ViewObject{ - @Composable - fun Accept(v: V) -} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/vo/Visitor.kt b/src/app/src/main/java/fr/iut/alldev/allin/vo/Visitor.kt deleted file mode 100644 index 00aa0a2..0000000 --- a/src/app/src/main/java/fr/iut/alldev/allin/vo/Visitor.kt +++ /dev/null @@ -1,3 +0,0 @@ -package fr.iut.alldev.allin.vo - -interface Visitor \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt b/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt new file mode 100644 index 0000000..deaf6f9 --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt @@ -0,0 +1,27 @@ +package fr.iut.alldev.allin.vo.bet + +import androidx.compose.runtime.Composable +import fr.iut.alldev.allin.data.model.bet.Bet +import fr.iut.alldev.allin.data.model.bet.CustomBet +import fr.iut.alldev.allin.data.model.bet.MatchBet +import fr.iut.alldev.allin.data.model.bet.YesNoBet + +interface BetDisplayer { + @Composable + fun DisplayBet(bet: Bet){ + when(bet){ + is CustomBet -> DisplayCustomBet(bet) + is MatchBet -> DisplayMatchBet(bet) + is YesNoBet -> DisplayYesNoBet(bet) + } + } + + @Composable + fun DisplayYesNoBet(b: YesNoBet) + + @Composable + fun DisplayMatchBet(b: MatchBet) + + @Composable + fun DisplayCustomBet(b: CustomBet) +} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetVO.kt b/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetVO.kt deleted file mode 100644 index 5df8223..0000000 --- a/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetVO.kt +++ /dev/null @@ -1,28 +0,0 @@ -package fr.iut.alldev.allin.vo.bet - -import androidx.compose.runtime.Composable -import fr.iut.alldev.allin.data.model.bet.Bet -import fr.iut.alldev.allin.data.model.bet.MatchBet -import fr.iut.alldev.allin.data.model.bet.YesNoBet -import fr.iut.alldev.allin.vo.ViewObject -import fr.iut.alldev.allin.vo.bet.visitor.DisplayBetVisitor - -abstract class BetVO(val bet: T) -: ViewObject { - @Composable - abstract override fun Accept(v: DisplayBetVisitor) -} - -class YesNoBetVO(bet: YesNoBet) : BetVO(bet){ - @Composable - override fun Accept(v: DisplayBetVisitor){ - v.VisitYesNoBet(b = bet) - } -} - -class MatchBetVO(bet: MatchBet) : BetVO(bet){ - @Composable - override fun Accept(v: DisplayBetVisitor){ - v.VisitMatchBet(b = bet) - } -} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/factory/BetVOFactory.kt b/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/factory/BetVOFactory.kt deleted file mode 100644 index 90cbf02..0000000 --- a/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/factory/BetVOFactory.kt +++ /dev/null @@ -1,30 +0,0 @@ -package fr.iut.alldev.allin.vo.bet.factory - -import fr.iut.alldev.allin.data.model.bet.Bet -import fr.iut.alldev.allin.data.model.bet.MatchBet -import fr.iut.alldev.allin.data.model.bet.YesNoBet -import fr.iut.alldev.allin.vo.bet.BetVO -import fr.iut.alldev.allin.vo.bet.MatchBetVO -import fr.iut.alldev.allin.vo.bet.YesNoBetVO - -private val betTypeToVOMap = mapOf( - YesNoBet::class.java to YesNoBetVOFactory(), - MatchBet::class.java to MatchBetVOFactory() -) -abstract class BetVOFactory { - abstract fun create(bet: @UnsafeVariance T): BetVO<@UnsafeVariance T> -} - -class YesNoBetVOFactory : BetVOFactory() { - override fun create(bet: YesNoBet) = - YesNoBetVO(bet) -} - -class MatchBetVOFactory : BetVOFactory() { - override fun create(bet: MatchBet) = - MatchBetVO(bet) -} - -fun Bet.toBetVO() = betTypeToVOMap[this.javaClass]?.create(this) - - diff --git a/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/visitor/BetVisitor.kt b/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/visitor/BetVisitor.kt deleted file mode 100644 index 7c8f584..0000000 --- a/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/visitor/BetVisitor.kt +++ /dev/null @@ -1,15 +0,0 @@ -package fr.iut.alldev.allin.vo.bet.visitor - -import androidx.compose.runtime.Composable -import fr.iut.alldev.allin.data.model.bet.MatchBet -import fr.iut.alldev.allin.data.model.bet.YesNoBet -import fr.iut.alldev.allin.vo.Visitor - - -interface DisplayBetVisitor : Visitor { - @Composable - fun VisitYesNoBet(b: YesNoBet) - - @Composable - fun VisitMatchBet(b: MatchBet) -} \ No newline at end of file diff --git a/src/app/src/main/res/drawable/allin_marquee.xml b/src/app/src/main/res/drawable/allin_marquee.xml new file mode 100644 index 0000000..fbd7a45 --- /dev/null +++ b/src/app/src/main/res/drawable/allin_marquee.xml @@ -0,0 +1,4307 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/app/src/main/res/font/plusjakartasans_bold.ttf b/src/app/src/main/res/font/plusjakartasans_bold.ttf deleted file mode 100644 index 386d3a6dacedacb3fb68ecf65acce0f301685363..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 94784 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 diff --git a/src/app/src/main/res/font/plusjakartasans_extrabold.ttf b/src/app/src/main/res/font/plusjakartasans_extrabold.ttf deleted file mode 100644 index a67cafd187835163a9beaedfd5e7672b044500e7..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 94788 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 RDpH{Q%XAqYk1|H`{{bHkIv)T4 diff --git a/src/app/src/main/res/font/plusjakartasans_extralight.ttf b/src/app/src/main/res/font/plusjakartasans_extralight.ttf deleted file mode 100644 index bb43929a8f5a8d53cae78d52f4a31b4b23567441..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 94772 zcmeFa2Yi%8*9SV~*-hE>4ur5tNC*T%b~lxtO7FcBLI{D7KnhK|f{2O=SWr|zv7jO% zC?X;vAU5n8Q4|3Yac!t53grH$Y_deKyzlGxz4zWP`Tb|k%rnpQbLPxEGqZ#eLIPkI zgmlf#%WwB#r*{cq9pL+M*M5Bm-ZZl|ijc}=LOLgP9XL2U{4AYINKy(Rp^x?**w+61 zoH3seLO(|MaRUcs4LbhYYyNQG0e5cU)PiZdhdtbk5HCFUTv}XEIZdR7=OM5?i%Vxu zT-Cd37a?265%T=IlZpx^L~jjijpuNav`O&r9N^Ic?hbG_pER{h zOUnxj=128j26_V0$e&s;Ynri@>_zxUgtwLzOf7n`&-sCb@CZW8`=*swR(U=*9CXf6 zLfZD3R#7x?B=??u`a?YI}_ zKKxU1fUd(E8|WJ_-=c59e20Z2o+d0BW-N<^8P7Vy%wmX#<+8Cb3)wX=m$IcWuVdH2 zyq-M<^KqW8bH?}={0q<*_yts2u`!)+qtaN7vJnzR%S0IsFVOppm71m`!x*7yM*NIk zn&za3!8C2Sg)xzK{Gj$XlN2uE7IAu#0Dg_8y+|aVq-k%mkKM0n3rS{Gn)Y#{eQ69G zp#A+w8hX2mGl0aPy%imZ-f>dXjYt&wgY>5aVII&lMLR9kG$YN)cujNSLxyPDsE>!5 z(0aPO)LdV7>VfcGba<4DBx_ofGC|Yc=p|vAwjjK>rUgaF08&n-k^)jjx|1r{rKE%u zk~}gCt_rxb@w^nA=&}crB7`rgbN7aO0^HT`?FGA-Ov0N(;p?J>ZyEfjAhrsWI}7nu z;dupo3nW#EH>=^UCY4uwE^=6in5JDJL_fqT-tU1pRZ5~X1A#L5)|aO~kFGbY4c@WV zy(LOgg%m4EJJJ^amB>Mb%tICEB%lPTCZUEZP`KC(>01f2HJ%ND zT_N)(QnwNtawuSR%h{#rx^h!MW*~o}Oaxpo+|vB~3!fMDMJx(TQ-Y8WnXU>c1FnRdeE*sI@D%YmO|-Y=jZ5 zVI?`ROLb|*yP{MjG6gHjFT!<2drU=ML>-9o4}dudm<@j`;;2CAsh|eIcF(z}QBn7H zaHK%eAI8-1ZC42{-Ii~g!l!2SRo-B_QYb@(vuKwJZeStzP7UN+*`M8UFw&wotBWRLYoj{ zS%{Ff(l$IRU>_q3F%FL>zK|E0WIlP6cBAv@O>`w)Pq)z5=oj=WjIC{$gQc_K>?L-D z8{CKc^B~@YH|GgFiQD*U{xIL;*Ez~7%0DVRs%cboR9sYIRNJWZsP<9aqXtHej4FvL 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

+vauS#>|Itz;&sRfDbrVaA7$rahY@(NEzWomt) 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

nLGMAF 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 diff --git a/src/app/src/main/res/values-fr/strings.xml b/src/app/src/main/res/values-fr/strings.xml index 07009f3..0b953ca 100644 --- a/src/app/src/main/res/values-fr/strings.xml +++ b/src/app/src/main/res/values-fr/strings.xml @@ -126,4 +126,10 @@ %s [icon] gagnés ! %s [icon] perdus ! + + FÉLICITATIONS + Vous remportez + Cote totale + Mise + Gains \ No newline at end of file diff --git a/src/app/src/main/res/values/font_certs.xml b/src/app/src/main/res/values/font_certs.xml new file mode 100644 index 0000000..141bfc0 --- /dev/null +++ b/src/app/src/main/res/values/font_certs.xml @@ -0,0 +1,17 @@ + + + + @array/com_google_android_gms_fonts_certs_dev + @array/com_google_android_gms_fonts_certs_prod + + + + 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 + + + \ No newline at end of file diff --git a/src/app/src/main/res/values/strings.xml b/src/app/src/main/res/values/strings.xml index bf11bd0..f1c5ad9 100644 --- a/src/app/src/main/res/values/strings.xml +++ b/src/app/src/main/res/values/strings.xml @@ -126,4 +126,12 @@ %s [icon] won ! %s [icon] lost ! + + CONGRATULATIONS + You win + Total odds + Stake + Winnings + + \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/api/AllInApi.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/api/AllInApi.kt index 9d3264a..413113e 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/api/AllInApi.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/api/AllInApi.kt @@ -21,7 +21,7 @@ interface AllInApi { suspend fun login(@Header("Authorization") token: String): ResponseUser @POST("bets/add") - suspend fun createBet(@Body body: RequestBet) + suspend fun createBet(@Header("Authorization") token: String, @Body body: RequestBet) @GET("bets/gets") suspend fun getAllBets(): List diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt index ba3c2e8..c5da50a 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt @@ -55,6 +55,5 @@ data class RequestBet( @Serializable(SimpleDateSerializer::class) val endRegistration: ZonedDateTime, @Serializable(SimpleDateSerializer::class) var endBet: ZonedDateTime, var isPrivate: Boolean, - var response: List, - val createdBy: String + var response: List ) diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt index 20f10bf..21684a7 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt @@ -3,7 +3,7 @@ package fr.iut.alldev.allin.data.model.bet import fr.iut.alldev.allin.data.api.model.RequestBet import java.time.ZonedDateTime -abstract class Bet( +sealed class Bet( open val id: Int? = null, open val creator: String, open val theme: String, @@ -21,8 +21,7 @@ abstract class Bet( endRegistration = endRegisterDate, endBet = endBetDate, isPrivate = !isPublic, - response = getResponses(), - createdBy = creator + response = getResponses() ) } } \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetStatus.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetStatus.kt index b42275f..66d27a8 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetStatus.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetStatus.kt @@ -6,4 +6,14 @@ sealed class BetStatus { data object InProgress : BetStatus() data object Waiting : BetStatus() + + companion object { + val entries = sequenceOf( + InProgress, + Waiting, + Finished(BetFinishedStatus.WON), + Finished(BetFinishedStatus.LOST) + ) + } + } \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/BetRepositoryImpl.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/BetRepositoryImpl.kt index bf33f40..1c21c87 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/BetRepositoryImpl.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/BetRepositoryImpl.kt @@ -16,7 +16,8 @@ class BetRepositoryImpl @Inject constructor( ) : BetRepository() { override suspend fun createBet(bet: Bet, token: String) { api.createBet( - bet.toRequestBet().copy(createdBy = token) + token = token, + body = bet.toRequestBet() ) } diff --git a/src/data/src/release/java/fr.iut.alldev.allin.data.di/ReleaseModule.kt b/src/data/src/release/java/fr.iut.alldev.allin.data.di/ReleaseModule.kt index 02df214..11bdf83 100644 --- a/src/data/src/release/java/fr.iut.alldev.allin.data.di/ReleaseModule.kt +++ b/src/data/src/release/java/fr.iut.alldev.allin.data.di/ReleaseModule.kt @@ -1,12 +1,8 @@ package fr.iut.alldev.allin.data.di import dagger.Module -import dagger.Provides import dagger.hilt.InstallIn import dagger.hilt.components.SingletonComponent -import okhttp3.OkHttpClient -import okhttp3.logging.HttpLoggingInterceptor -import javax.inject.Singleton @Module(includes = [ReleaseNetworkModule::class]) @InstallIn(SingletonComponent::class) diff --git a/src/data/src/release/java/fr.iut.alldev.allin.data.di/ReleaseNetworkModule.kt b/src/data/src/release/java/fr.iut.alldev.allin.data.di/ReleaseNetworkModule.kt index 4bb6870..adfb9d0 100644 --- a/src/data/src/release/java/fr.iut.alldev.allin.data.di/ReleaseNetworkModule.kt +++ b/src/data/src/release/java/fr.iut.alldev.allin.data.di/ReleaseNetworkModule.kt @@ -4,8 +4,8 @@ import dagger.Module import dagger.Provides import dagger.hilt.InstallIn import dagger.hilt.components.SingletonComponent +import fr.iut.alldev.allin.data.api.interceptors.ErrorInterceptor import okhttp3.OkHttpClient -import okhttp3.logging.HttpLoggingInterceptor import javax.inject.Singleton @Module diff --git a/src/gradle/libs.versions.toml b/src/gradle/libs.versions.toml index cb615ee..3ecc6ce 100644 --- a/src/gradle/libs.versions.toml +++ b/src/gradle/libs.versions.toml @@ -10,9 +10,10 @@ kotlin = "1.9.20" androidxCore = "1.12.0" androidxActivity = "1.8.2" -androidxSecurity = "1.0.0" +androidxSecurity = "1.1.0-alpha06" composeBom = "2023.10.01" +compose = "1.5.4" composePreview = "1.6.0-beta03" composeCompiler = "1.5.5" composeNavigation = "2.7.6" @@ -31,7 +32,7 @@ room = "2.6.1" okHttp = "4.11.0" # Plugins -gradlePlugin = "8.1.2" +gradlePlugin = "8.1.4" publishPlugin = "1.1" resgenPlugin = "2.5" @@ -54,6 +55,9 @@ test-androidx-junit = { group = "androidx.test.ext", name = "junit-ktx", version test-espresso = { group = "androidx.test.espresso", name = "espresso-core", version.ref = "espressoCore" } hilt-androidTesting = { group = "com.google.dagger", name = "hilt-android-testing", version.ref = "hilt" } hilt-androidCompiler = { group = "com.google.dagger", name = "hilt-android-compiler", version.ref = "hilt" } +ui-test-junit = { group = "androidx.compose.ui", name = "ui-test-junit4", version.ref = "compose" } +ui-test-manifest = { group = "androidx.compose.ui", name = "ui-test-manifest", version.ref = "compose" } + # Compose compose-bom = { module = "androidx.compose:compose-bom", version.ref = "composeBom" } @@ -95,7 +99,6 @@ plugin-kotlin = { module = "org.jetbrains.kotlin:kotlin-gradle-plugin", version. plugin-kotlinSerialization = { module = "org.jetbrains.kotlin:kotlin-serialization", version.ref = "kotlin" } plugin-hilt = { module = "com.google.dagger:hilt-android-gradle-plugin", version.ref = "hilt" } - [bundles] android = ["androidx-core", "androidx-activity", "androidx-security"] diff --git a/src/keys/debug.keystore b/src/keys/debug.keystore new file mode 100644 index 0000000000000000000000000000000000000000..4a3c6c03f3d73f23c4830a521e1f82236cd3b6fa GIT binary patch literal 2779 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 LI*=8}5<&kLAs+?Z literal 0 HcmV?d00001 diff --git a/src/keys/keystore.properties b/src/keys/keystore.properties new file mode 100644 index 0000000..eadbbfe --- /dev/null +++ b/src/keys/keystore.properties @@ -0,0 +1,4 @@ +debugStoreFile=../keys/debug.keystore +releaseStoreFile=../keys/release.keystore +aliasRelease=placeYourBets +passwordRelease=placeYourBets \ No newline at end of file diff --git a/src/keys/release.keystore b/src/keys/release.keystore new file mode 100644 index 0000000000000000000000000000000000000000..005b9a8009f973a77bef8991aa7fb19f6d58df0e GIT binary patch literal 2775 zcma)+c{tRK7RP7C%-Dt)!`R6>4El|2NX+Y1V;^K`A=$TNEs-Tn=tZ`SVGzciEqk_# zWN)mAicqqavNeggJc8125zrZF7|!)^F*Li7xccgA+1dnE#!~tzJB`y z?WZxm;TAx#d2)8TazKMTUhs1QwHQ;)lVG)3@anc&h7_!&R`rgtfGwie3`EwZz9ejQPAcFv+p17}O|Nt~u_3P zZNDjiW#px15vuUwhpWKQRE6c5&o+Mj&t~(cQwcjaUfw|FtseKfC zzAG30MZrN~_07P@U(^_@KPX%I% zO%Wp{!N{B@Uyn8;u0{2>I^rP5F*4sdp{+Jd{PL>Gp&U=MKu3azr71yWWr+Cp+xL1= zQ#EnVa%p=dqOEMqBU9xhZ{g3uaMauGXnui|*7Hvk>4py%pqbx>gqeqi^>?HCay==E zL!2Wz%kTLbC>S{Y&nZ6+1x4C; zUv-zn;Qj2qab5{^fK1scJr9Zz}0DG0^g)t zjJ6&s1?ce^N=}(o(;3gaL1`x~mbYDYOZz&~FokpObbTG!?-Nq6)qTV}lu4r8+t8aq zcQ=-Nb%-lRJ@Z+Z|<69p$ii?V(~2kRazE`h&$Lgb*$!d7-ADM5H@jwO(|2 z*UZK<+`r=4K1tFdM>`?YAKUEKLm*^C4j@CXznQlVH&fossMFU;$NDSw&g8L;W-93W z?uyihb~J=5nMafALtQ^fsf{=$X!~0oqx!$o(H{Qdqut}__Rj1DG8H}~TAxh~U!~h1 zrA2JyN6RlRrS<-~>+ZN8XvJ+kJF<1x#+SBCI8FO{)!Mf9_(HLgT4}4RRPv*RC4r8{ zVUUa46WvY*nX2%~QN}5~X*69T_Y!kkw(PR7j(NZW3miX>#&X(CFkLpxJ{`{j1$rRk zUNZx$r4lyI%r*~f5yP5JiAwA=8Aec|tk&x7v_@96yB|EdX-XL-uFLcai!D^VDf+2_ zw5uBLaMWs7Pv+r7lp+n*E9Awnb8^sGEzJ&ch^JaGlx zXVBVJj&tiLY)@2Z!DzwyQTpN7G5_1ygZwSoLdIHt{BxWovS!mYx zEuI>8D~MhMo@yT_G57_=hbABIRZC(Dqw;lZ^{+5}J(-3#uLlqtx6x;(g?0<>^UqxU zV8*b*?ut^Y3LdOzPxtGF^-2z#poc?656X9452w1xF zjUX+%s+{^N$2|SUtuI&!&~wTFaXeDvUgv}3ELv@xh|DnQyKe-&ZMW7ojOH#oE*z`7 zX8o(OdMsWyF5d6w>bWGrxeo2CL({ypK5^3$bVW#K+oKHKFfN{nE`V`xe;%WovFCYC zcLF<_WnzXZe^L Date: Tue, 16 Jan 2024 15:44:52 +0100 Subject: [PATCH 2/3] Mock API and Bet participation bottom sheet --- .../fr/iut/alldev/allin/test/mock/Bets.kt | 2 +- .../vo/bet/displayer/BetVOTestVisitor.kt | 6 +- .../fr/iut/alldev/allin/ext/BetTypeExt.kt | 2 +- .../java/fr/iut/alldev/allin/ext/FloatExt.kt | 9 + .../java/fr/iut/alldev/allin/ext/StringExt.kt | 21 ++ .../ui/betCreation/BetCreationViewModel.kt | 2 +- .../tabs/BetCreationScreenQuestionTab.kt | 17 +- .../sections/QuestionTabThemePhraseSection.kt | 26 +-- .../ui/betStatus/BetStatusBottomSheet.kt | 40 +++- .../BetStatusParticipationAnswers.kt | 110 ++++++++++ .../BetStatusParticipationBottomSheet.kt | 194 +++++++++++++----- .../vo/BetStatusBottomSheetBetDisplayer.kt | 63 ++---- .../iut/alldev/allin/ui/core/AllInButton.kt | 23 ++- .../alldev/allin/ui/core/AllInSelectionBox.kt | 93 ++++++++- .../alldev/allin/ui/core/AllInTextField.kt | 171 ++++++++------- .../iut/alldev/allin/ui/login/LoginScreen.kt | 15 +- .../fr/iut/alldev/allin/ui/main/MainScreen.kt | 24 ++- .../iut/alldev/allin/ui/main/MainViewModel.kt | 2 +- .../allin/ui/preview/BetPreviewProvider.kt | 4 +- .../preview/BetWithStatusPreviewProvider.kt | 2 +- .../allin/ui/register/RegisterScreen.kt | 28 +-- .../iut/alldev/allin/vo/bet/BetDisplayer.kt | 6 +- .../iut/alldev/allin/data/api/MockAllInApi.kt | 96 +++++++++ .../iut/alldev/allin/data/api/model/ApiBet.kt | 8 +- .../alldev/allin/data/api/model/ApiUser.kt | 3 +- .../fr/iut/alldev/allin/data/di/ApiModule.kt | 11 +- .../fr/iut/alldev/allin/data/model/bet/Bet.kt | 2 +- .../alldev/allin/data/model/bet/BetFactory.kt | 2 +- .../alldev/allin/data/model/bet/CustomBet.kt | 6 +- .../alldev/allin/data/model/bet/MatchBet.kt | 4 +- .../alldev/allin/data/model/bet/YesNoBet.kt | 9 +- 31 files changed, 729 insertions(+), 272 deletions(-) create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ext/FloatExt.kt create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ext/StringExt.kt create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationAnswers.kt create mode 100644 src/data/src/main/java/fr/iut/alldev/allin/data/api/MockAllInApi.kt diff --git a/src/app/src/androidTest/java/fr/iut/alldev/allin/test/mock/Bets.kt b/src/app/src/androidTest/java/fr/iut/alldev/allin/test/mock/Bets.kt index 9be1682..846c540 100644 --- a/src/app/src/androidTest/java/fr/iut/alldev/allin/test/mock/Bets.kt +++ b/src/app/src/androidTest/java/fr/iut/alldev/allin/test/mock/Bets.kt @@ -37,7 +37,7 @@ object Bets { isPublic = true, betStatus = BetStatus.InProgress, creator = "creator", - possibleAnswers = setOf( + possibleAnswers = listOf( "Answer 1", "Answer 2", "Answer 3", diff --git a/src/app/src/androidTest/java/fr/iut/alldev/allin/vo/bet/displayer/BetVOTestVisitor.kt b/src/app/src/androidTest/java/fr/iut/alldev/allin/vo/bet/displayer/BetVOTestVisitor.kt index 296593c..b8abc92 100644 --- a/src/app/src/androidTest/java/fr/iut/alldev/allin/vo/bet/displayer/BetVOTestVisitor.kt +++ b/src/app/src/androidTest/java/fr/iut/alldev/allin/vo/bet/displayer/BetVOTestVisitor.kt @@ -12,17 +12,17 @@ import fr.iut.alldev.allin.vo.bet.BetDisplayer class BetTestDisplayer : BetDisplayer { @Composable - override fun DisplayYesNoBet(b: YesNoBet) { + override fun DisplayYesNoBet(bet: YesNoBet) { Text("This is a YesNo Bet", Modifier.testTag(TestTags.YES_NO_BET.tag)) } @Composable - override fun DisplayMatchBet(b: MatchBet) { + override fun DisplayMatchBet(bet: MatchBet) { Text("This is a Match Bet", Modifier.testTag(TestTags.MATCH_BET.tag)) } @Composable - override fun DisplayCustomBet(b: CustomBet) { + override fun DisplayCustomBet(bet: CustomBet) { Text("This is a Custom Bet", Modifier.testTag(TestTags.CUSTOM_BET.tag)) } } \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ext/BetTypeExt.kt b/src/app/src/main/java/fr/iut/alldev/allin/ext/BetTypeExt.kt index b91ac51..43c66a0 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ext/BetTypeExt.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ext/BetTypeExt.kt @@ -12,7 +12,7 @@ import fr.iut.alldev.allin.data.model.bet.BetType @StringRes fun BetType.getTitleId(): Int { return when (this) { - BetType.YES_NO -> R.string.yes_no + BetType.YES_NO -> R.string.yes_no BetType.MATCH -> R.string.sport_match BetType.CUSTOM -> R.string.custom_answers } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ext/FloatExt.kt b/src/app/src/main/java/fr/iut/alldev/allin/ext/FloatExt.kt new file mode 100644 index 0000000..542eec9 --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ext/FloatExt.kt @@ -0,0 +1,9 @@ +package fr.iut.alldev.allin.ext + +import java.text.DecimalFormat +import java.text.DecimalFormatSymbols +import java.util.Locale + +fun Float.formatToSimple(locale: Locale): String { + return DecimalFormat("0.##", DecimalFormatSymbols.getInstance(locale)).format(this) +} diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ext/StringExt.kt b/src/app/src/main/java/fr/iut/alldev/allin/ext/StringExt.kt new file mode 100644 index 0000000..4d0bab2 --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ext/StringExt.kt @@ -0,0 +1,21 @@ +package fr.iut.alldev.allin.ext + +import java.text.DecimalFormat +import java.text.DecimalFormatSymbols +import java.util.Locale + +fun String.verifyIsFloat(locale: Locale): String? { + val pattern = Regex("^\\d+(\\.|\\,)?\\d*\$") + val decimalSeparator = DecimalFormatSymbols.getInstance(locale).decimalSeparator.toString() + + return if (this.matches(pattern)) { + this.replace(Regex("[.,]"), decimalSeparator).format() + } else if (this.isEmpty()) { + this + } else null +} + +fun String.toFloatOrNull(locale: Locale): Float? { + val format = DecimalFormat("0.##", DecimalFormatSymbols.getInstance(locale)) + return format.parse(this)?.toFloat() +} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/BetCreationViewModel.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/BetCreationViewModel.kt index 620bd63..71d3aae 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/BetCreationViewModel.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/BetCreationViewModel.kt @@ -118,7 +118,7 @@ class BetCreationViewModel @Inject constructor( isPublic = isPublic.value, nameTeam1 = "", nameTeam2 = "", - possibleAnswers = setOf(), + possibleAnswers = listOf(), creator = currentUser.username ) betRepository.createBet(bet, keystoreManager.getToken() ?: "") diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/BetCreationScreenQuestionTab.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/BetCreationScreenQuestionTab.kt index b893b5d..5edafd5 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/BetCreationScreenQuestionTab.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/BetCreationScreenQuestionTab.kt @@ -21,25 +21,25 @@ fun BetCreationScreenQuestionTab( nbFriends: Int, betTheme: String, betThemeError: String?, - setBetTheme: (String)->Unit, + setBetTheme: (String) -> Unit, betPhrase: String, betPhraseError: String?, - setBetPhrase: (String)->Unit, + setBetPhrase: (String) -> Unit, isPublic: Boolean, - setIsPublic: (Boolean)->Unit, + setIsPublic: (Boolean) -> Unit, registerDate: ZonedDateTime, registerDateError: String?, betDate: ZonedDateTime, betDateError: String?, selectedFriends: MutableList, - setRegisterDateDialog: (Boolean)->Unit, - setEndDateDialog: (Boolean)->Unit, - setRegisterTimeDialog: (Boolean)->Unit, - setEndTimeDialog: (Boolean)->Unit, + setRegisterDateDialog: (Boolean) -> Unit, + setEndDateDialog: (Boolean) -> Unit, + setRegisterTimeDialog: (Boolean) -> Unit, + setEndTimeDialog: (Boolean) -> Unit, interactionSource: MutableInteractionSource ) { val bringIntoViewRequester = remember { BringIntoViewRequester() } - Column(modifier){ + Column(modifier) { QuestionTabThemePhraseSection( betTheme = betTheme, betThemeError = betThemeError, @@ -47,7 +47,6 @@ fun BetCreationScreenQuestionTab( betPhrase = betPhrase, betPhraseError = betPhraseError, setBetPhrase = setBetPhrase, - bringIntoViewRequester = bringIntoViewRequester, interactionSource = interactionSource ) Spacer(modifier = Modifier.height(35.dp)) diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/sections/QuestionTabThemePhraseSection.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/sections/QuestionTabThemePhraseSection.kt index 809da0d..3eddd1f 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/sections/QuestionTabThemePhraseSection.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/sections/QuestionTabThemePhraseSection.kt @@ -6,7 +6,6 @@ import androidx.compose.foundation.layout.Spacer import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding -import androidx.compose.foundation.relocation.BringIntoViewRequester import androidx.compose.material.icons.Icons import androidx.compose.material.icons.automirrored.outlined.HelpOutline import androidx.compose.runtime.Composable @@ -24,11 +23,10 @@ import fr.iut.alldev.allin.ui.core.AllInTitleInfo internal fun QuestionTabThemePhraseSection( betTheme: String, betThemeError: String?, - setBetTheme: (String)->Unit, + setBetTheme: (String) -> Unit, betPhrase: String, betPhraseError: String?, - setBetPhrase: (String)->Unit, - bringIntoViewRequester: BringIntoViewRequester, + setBetPhrase: (String) -> Unit, interactionSource: MutableInteractionSource ) { AllInTitleInfo( @@ -41,13 +39,12 @@ internal fun QuestionTabThemePhraseSection( AllInTextField( placeholder = stringResource(id = R.string.Theme_placeholder), value = betTheme, - onValueChange = setBetTheme, - bringIntoViewRequester = bringIntoViewRequester, - borderColor = AllInTheme.colors.white, + modifier = Modifier.fillMaxWidth(), maxChar = 20, placeholderFontSize = 13.sp, + onValueChange = setBetTheme, errorText = betThemeError, - modifier = Modifier.fillMaxWidth() + borderColor = AllInTheme.colors.white ) Spacer(modifier = Modifier.height(10.dp)) AllInTitleInfo( @@ -60,15 +57,14 @@ internal fun QuestionTabThemePhraseSection( AllInTextField( placeholder = stringResource(id = R.string.Bet_Phrase_placeholder), value = betPhrase, - borderColor = AllInTheme.colors.white, - onValueChange = setBetPhrase, - bringIntoViewRequester = bringIntoViewRequester, - multiLine = true, + modifier = Modifier + .fillMaxWidth() + .height(100.dp), maxChar = 100, placeholderFontSize = 13.sp, + multiLine = true, + onValueChange = setBetPhrase, errorText = betPhraseError, - modifier = Modifier - .fillMaxWidth() - .height(100.dp) + borderColor = AllInTheme.colors.white ) } \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt index 491cb19..da23df3 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt @@ -7,7 +7,10 @@ import androidx.compose.runtime.* import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.Color import fr.iut.alldev.allin.data.model.bet.Bet +import fr.iut.alldev.allin.data.model.bet.BetStatus import fr.iut.alldev.allin.ui.betStatus.components.BetStatusBottomSheetBack +import fr.iut.alldev.allin.ui.betStatus.components.BetStatusParticipationBottomSheet +import fr.iut.alldev.allin.ui.betStatus.components.getParticipationAnswers import fr.iut.alldev.allin.ui.core.AllInBottomSheet @@ -21,7 +24,12 @@ fun BetStatusBottomSheet( sheetVisibility: Boolean, sheetBackVisibility: Boolean, bet: Bet?, - onDismiss: ()->Unit, + paddingValues: PaddingValues, + userCoinAmount: MutableIntState, + onParticipate: (Int) -> Unit, + onDismiss: () -> Unit, + participateSheetVisibility: Boolean, + setParticipateSheetVisibility: (Boolean) -> Unit, displayBet: @Composable (Bet) -> Unit ) { AnimatedVisibility( @@ -45,13 +53,41 @@ fun BetStatusBottomSheet( onDismiss = onDismiss, state = state, scrimColor = Color.Transparent - ){ + ) { + + var selectedAnswer by remember { mutableStateOf(0) } + var stake by remember { mutableStateOf(null) } + Column( Modifier.fillMaxHeight(SHEET_HEIGHT) ) { bet?.let { + val elements = bet.getParticipationAnswers() + displayBet(it) + BetStatusParticipationBottomSheet( + sheetVisibility = participateSheetVisibility && bet.betStatus == BetStatus.Waiting && state.hasExpandedState, + safeBottomPadding = paddingValues.calculateBottomPadding(), + betPhrase = bet.phrase, + coinAmount = userCoinAmount.intValue, + onDismiss = { setParticipateSheetVisibility(false) }, + state = rememberModalBottomSheetState(skipPartiallyExpanded = true), + elements = elements, + selectedElement = elements.getOrNull(selectedAnswer), + stake = stake, + setStake = { stake = it }, + setElement = { idx -> selectedAnswer = idx }, + enabled = stake != null && + (stake ?: 0) <= userCoinAmount.intValue + ) { + stake?.let { + onParticipate(it) + } + } + } } + } + } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationAnswers.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationAnswers.kt new file mode 100644 index 0000000..fa0511f --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationAnswers.kt @@ -0,0 +1,110 @@ +package fr.iut.alldev.allin.ui.betStatus.components + +import android.content.res.Configuration +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.RowScope +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.material3.Text + +import androidx.compose.runtime.Composable +import androidx.compose.ui.Modifier +import androidx.compose.ui.res.stringResource +import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.tooling.preview.PreviewParameter +import androidx.compose.ui.unit.sp +import fr.iut.alldev.allin.R +import fr.iut.alldev.allin.data.model.bet.Bet +import fr.iut.alldev.allin.data.model.bet.CustomBet +import fr.iut.alldev.allin.data.model.bet.MatchBet +import fr.iut.alldev.allin.data.model.bet.NO_VALUE +import fr.iut.alldev.allin.data.model.bet.YES_VALUE +import fr.iut.alldev.allin.data.model.bet.YesNoBet +import fr.iut.alldev.allin.theme.AllInTheme +import fr.iut.alldev.allin.ui.preview.BetPreviewProvider + +private val participationAnswerFontSize = 25.sp + +@Composable +fun Bet.getParticipationAnswers(): List<@Composable RowScope.() -> Unit> = + when (this) { + is CustomBet -> this.possibleAnswers.map { + { + Text( + text = it, + color = AllInTheme.colors.allInBlue, + style = AllInTheme.typography.h1, + fontSize = participationAnswerFontSize + ) + } + } + + is MatchBet -> listOf( + { + Text( + text = this@getParticipationAnswers.nameTeam1, + color = AllInTheme.colors.allInBlue, + style = AllInTheme.typography.h1, + fontSize = participationAnswerFontSize + ) + }, + { + Text( + text = this@getParticipationAnswers.nameTeam2, + color = AllInTheme.colors.allInBarPink, + style = AllInTheme.typography.h1, + fontSize = participationAnswerFontSize + ) + } + ) + + is YesNoBet -> listOf( + { + Text( + text = stringResource(id = R.string.Yes).uppercase(), + color = AllInTheme.colors.allInBlue, + style = AllInTheme.typography.h1, + fontSize = participationAnswerFontSize + ) + }, + { + Text( + text = stringResource(id = R.string.No).uppercase(), + color = AllInTheme.colors.allInBarPink, + style = AllInTheme.typography.h1, + fontSize = participationAnswerFontSize + ) + } + ) + } + +fun Bet.getAnswerFromParticipationIdx(idx: Int) = + when (this) { + is CustomBet -> this.possibleAnswers.getOrElse(idx) { "" } + is MatchBet -> when (idx) { + 0 -> this.nameTeam1 + 1 -> this.nameTeam2 + else -> "" + } + + is YesNoBet -> when (idx) { + 0 -> YES_VALUE + 1 -> NO_VALUE + else -> "" + } + } + +@Preview +@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +private fun ParticipationAnswersPreview( + @PreviewParameter(BetPreviewProvider::class) bet: Bet, +) { + AllInTheme { + Column { + bet.getParticipationAnswers().forEach { + Row(Modifier.fillMaxWidth()) { it() } + } + } + } +} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt index 4ab56ae..0b2db92 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt @@ -1,13 +1,17 @@ package fr.iut.alldev.allin.ui.betStatus.components +import android.content.res.Configuration import androidx.compose.foundation.background import androidx.compose.foundation.layout.* import androidx.compose.material3.* import androidx.compose.runtime.Composable +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember import androidx.compose.runtime.rememberCoroutineScope import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.res.stringResource +import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.Dp import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp @@ -16,6 +20,8 @@ import fr.iut.alldev.allin.theme.AllInTheme import fr.iut.alldev.allin.ui.core.AllInBottomSheet import fr.iut.alldev.allin.ui.core.AllInButton import fr.iut.alldev.allin.ui.core.AllInCoinCount +import fr.iut.alldev.allin.ui.core.AllInIntTextField +import fr.iut.alldev.allin.ui.core.AllInSelectionBox import fr.iut.alldev.allin.ui.core.topbar.AllInTopBarCoinCounter import kotlinx.coroutines.launch @@ -28,8 +34,13 @@ fun BetStatusParticipationBottomSheet( coinAmount: Int, onDismiss: () -> Unit, state: SheetState, - onParticipate: () -> Unit, - content: @Composable () -> Unit + enabled: Boolean, + stake: Int?, + setStake: (Int?) -> Unit, + elements: List<@Composable RowScope.() -> Unit>, + selectedElement: (@Composable RowScope.() -> Unit)?, + setElement: (Int) -> Unit, + onParticipate: () -> Unit ) { val scope = rememberCoroutineScope() AllInBottomSheet( @@ -37,6 +48,96 @@ fun BetStatusParticipationBottomSheet( onDismiss = onDismiss, state = state, containerColor = AllInTheme.themeColors.background2 + ) { + BetStatusParticipationBottomSheetContent( + safeBottomPadding = safeBottomPadding, + betPhrase = betPhrase, + coinAmount = coinAmount, + elements = elements, + selectedElement = selectedElement, + setElement = setElement, + enabled = enabled, + stake = stake, + setStake = setStake + ) { + scope.launch { + onParticipate() + state.hide() + onDismiss() + } + } + } +} + +@Composable +private fun ColumnScope.BetStatusParticipationBottomSheetContent( + safeBottomPadding: Dp, + betPhrase: String, + coinAmount: Int, + enabled: Boolean, + stake: Int?, + setStake: (Int?) -> Unit, + selectedElement: (@Composable RowScope.() -> Unit)?, + elements: List<@Composable RowScope.() -> Unit>, + setElement: (Int) -> Unit, + onButtonClick: () -> Unit +) { + val (answersBoxIsOpen, setAnswersBoxIsOpen) = remember { mutableStateOf(false) } + + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.SpaceBetween, + verticalAlignment = Alignment.CenterVertically + ) { + Text( + text = stringResource(id = R.string.place_your_bets), + style = AllInTheme.typography.h2, + color = AllInTheme.themeColors.onMainSurface, + fontSize = 20.sp, + modifier = Modifier.padding(start = 18.dp) + ) + AllInTopBarCoinCounter( + amount = coinAmount, + backgroundColor = AllInTheme.colors.allInBlue, + textColor = AllInTheme.colors.white, + iconColor = AllInTheme.colors.white, + ) + } + Column( + modifier = Modifier.padding(horizontal = 18.dp) + ) { + Text( + text = betPhrase, + style = AllInTheme.typography.p2, + color = AllInTheme.themeColors.onMainSurface, + modifier = Modifier.padding(vertical = 30.dp) + ) + AllInSelectionBox( + isOpen = answersBoxIsOpen, + setIsOpen = setAnswersBoxIsOpen, + selected = selectedElement, + setSelected = { setElement(elements.indexOf(it)) }, + elements = elements, + borderWidth = 1.dp + ) + Spacer(modifier = Modifier.height(8.dp)) + AllInIntTextField( + value = stake, + setValue = setStake, + placeholder = stringResource(id = R.string.bet_result_stake), + trailingIcon = AllInTheme.icons.allCoins(), + modifier = Modifier.fillMaxWidth(), + maxChar = null + ) + } + Spacer(modifier = Modifier.height(100.dp)) + HorizontalDivider(color = AllInTheme.themeColors.border) + Column( + modifier = Modifier + .background(AllInTheme.themeColors.background) + .padding(horizontal = 7.dp) + .padding(bottom = safeBottomPadding, top = 7.dp), + verticalArrangement = Arrangement.spacedBy(7.dp) ) { Row( modifier = Modifier.fillMaxWidth(), @@ -44,65 +145,44 @@ fun BetStatusParticipationBottomSheet( verticalAlignment = Alignment.CenterVertically ) { Text( - text = stringResource(id = R.string.place_your_bets), - style = AllInTheme.typography.h2, - color = AllInTheme.themeColors.onMainSurface, - fontSize = 20.sp, - modifier = Modifier.padding(start = 18.dp) + text = stringResource(id = R.string.Possible_winnings), + style = AllInTheme.typography.p1, + color = AllInTheme.themeColors.onBackground ) - AllInTopBarCoinCounter( - amount = coinAmount, - backgroundColor = AllInTheme.colors.allInBlue, - textColor = AllInTheme.colors.white, - iconColor = AllInTheme.colors.white, + AllInCoinCount( + amount = 121, + color = AllInTheme.themeColors.onBackground ) } - Spacer(modifier = Modifier.height(30.dp)) - Text( - text = betPhrase, - style = AllInTheme.typography.p2, - color = AllInTheme.themeColors.onMainSurface, - modifier = Modifier.padding(horizontal = 18.dp) + AllInButton( + enabled = enabled, + color = AllInTheme.colors.allInPurple, + text = stringResource(id = R.string.Participate), + textColor = AllInTheme.colors.white, + radius = 5.dp, + onClick = onButtonClick ) - Spacer(modifier = Modifier.height(100.dp)) - HorizontalDivider(color = AllInTheme.themeColors.border) - Column( - modifier = Modifier - .background(AllInTheme.themeColors.background) - .padding(horizontal = 7.dp) - .padding(bottom = safeBottomPadding, top = 7.dp), - verticalArrangement = Arrangement.spacedBy(7.dp) - ) { - Row( - modifier = Modifier.fillMaxWidth(), - horizontalArrangement = Arrangement.SpaceBetween, - verticalAlignment = Alignment.CenterVertically - ) { - Text( - text = stringResource(id = R.string.Possible_winnings), - style = AllInTheme.typography.p1, - color = AllInTheme.themeColors.onBackground - ) - AllInCoinCount( - amount = 121, - color = AllInTheme.themeColors.onBackground - ) - } - Box(modifier = Modifier.fillMaxSize()) { - content() - } - AllInButton( - color = AllInTheme.colors.allInPurple, - text = stringResource(id = R.string.Participate), - textColor = AllInTheme.colors.white, - radius = 5.dp - ) { - scope.launch { - onParticipate() - state.hide() - onDismiss() - } - } + } +} + +@Preview +@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) +@Composable +private fun BetStatusParticipationBottomSheetContentPreview() { + AllInTheme { + Column { + BetStatusParticipationBottomSheetContent( + safeBottomPadding = 0.dp, + betPhrase = "Bet phrase", + coinAmount = 3620, + onButtonClick = {}, + elements = emptyList(), + setElement = {}, + selectedElement = null, + enabled = true, + stake = 123, + setStake = {} + ) } } } \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/vo/BetStatusBottomSheetBetDisplayer.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/vo/BetStatusBottomSheetBetDisplayer.kt index 00c80e4..4c9a268 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/vo/BetStatusBottomSheetBetDisplayer.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/vo/BetStatusBottomSheetBetDisplayer.kt @@ -10,7 +10,6 @@ import androidx.compose.material.icons.filled.WorkspacePremium import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.HorizontalDivider import androidx.compose.material3.Text -import androidx.compose.material3.rememberModalBottomSheetState import androidx.compose.runtime.* import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier @@ -29,7 +28,6 @@ import fr.iut.alldev.allin.data.model.bet.YesNoBet import fr.iut.alldev.allin.ext.getDateEndLabelId import fr.iut.alldev.allin.ext.getDateStartLabelId import fr.iut.alldev.allin.theme.AllInTheme -import fr.iut.alldev.allin.ui.betStatus.components.BetStatusParticipationBottomSheet import fr.iut.alldev.allin.ui.betStatus.components.BetStatusWinner import fr.iut.alldev.allin.ui.betStatus.components.YesNoDetailsLine import fr.iut.alldev.allin.ui.betStatus.components.YesNoStatBar @@ -41,28 +39,22 @@ import fr.iut.alldev.allin.ui.preview.BetWithStatusPreviewProvider import fr.iut.alldev.allin.vo.bet.BetDisplayer class BetStatusBottomSheetBetDisplayer( - val userCoinAmount: MutableIntState, - val onParticipate: (Int) -> Unit, + val openParticipateSheet: () -> Unit ) : BetDisplayer { - val participateBottomSheetVisibility = mutableStateOf(false) val paddingValues = mutableStateOf(PaddingValues()) @OptIn(ExperimentalMaterial3Api::class) @Composable - override fun DisplayYesNoBet(b: YesNoBet) { - - val (participateSheetVisibility, setParticipateSheetVisibility) = remember { - this.participateBottomSheetVisibility - } + override fun DisplayYesNoBet(bet: YesNoBet) { val safeBottomPadding = paddingValues.value.calculateBottomPadding() Box(Modifier.padding(bottom = safeBottomPadding)) { Column { Column(Modifier.padding(horizontal = 20.dp)) { BetTitleHeader( - title = b.phrase, - category = b.theme, - creator = b.creator, + title = bet.phrase, + category = bet.theme, + creator = bet.creator, modifier = Modifier.fillMaxWidth() ) Spacer(modifier = Modifier.height(20.dp)) @@ -70,22 +62,22 @@ class BetStatusBottomSheetBetDisplayer( horizontalAlignment = Alignment.End ) { BetDateTimeRow( - label = stringResource(id = b.betStatus.getDateStartLabelId()), - date = b.endRegisterDate.formatToMediumDateNoYear(), - time = b.endRegisterDate.formatToTime(), + label = stringResource(id = bet.betStatus.getDateStartLabelId()), + date = bet.endRegisterDate.formatToMediumDateNoYear(), + time = bet.endRegisterDate.formatToTime(), modifier = Modifier.width(IntrinsicSize.Max) ) Spacer(modifier = Modifier.height(15.dp)) BetDateTimeRow( - label = stringResource(id = b.betStatus.getDateEndLabelId()), - date = b.endBetDate.formatToMediumDateNoYear(), - time = b.endBetDate.formatToTime(), + label = stringResource(id = bet.betStatus.getDateEndLabelId()), + date = bet.endBetDate.formatToMediumDateNoYear(), + time = bet.endBetDate.formatToTime(), modifier = Modifier.width(IntrinsicSize.Max) ) } Spacer(modifier = Modifier.height(20.dp)) } - if (b.betStatus is BetStatus.Finished) { + if (bet.betStatus is BetStatus.Finished) { BetStatusWinner( answer = stringResource(id = R.string.Yes), color = AllInTheme.colors.allInBlue, @@ -128,42 +120,26 @@ class BetStatusBottomSheetBetDisplayer( } } } - if (b.betStatus !is BetStatus.Finished) { + if (bet.betStatus !is BetStatus.Finished) { RainbowButton( modifier = Modifier .align(Alignment.BottomCenter) .padding(horizontal = 7.dp), text = stringResource(id = R.string.Participate), - enabled = b.betStatus == BetStatus.Waiting, - onClick = { - setParticipateSheetVisibility(true) - } + enabled = bet.betStatus == BetStatus.Waiting, + onClick = openParticipateSheet ) } } - - BetStatusParticipationBottomSheet( - sheetVisibility = participateSheetVisibility && b.betStatus == BetStatus.Waiting, - safeBottomPadding = safeBottomPadding, - betPhrase = b.phrase, - coinAmount = userCoinAmount.intValue, - onDismiss = { setParticipateSheetVisibility(false) }, - state = rememberModalBottomSheetState(), - onParticipate = { - onParticipate(100) - } - ) { - - } } @Composable - override fun DisplayMatchBet(b: MatchBet) { + override fun DisplayMatchBet(bet: MatchBet) { Text("This is a MATCH BET") } @Composable - override fun DisplayCustomBet(b: CustomBet) { + override fun DisplayCustomBet(bet: CustomBet) { Text("This is a CUSTOM BET") } } @@ -176,9 +152,6 @@ private fun BetStatusBottomSheetPreview( ) { AllInTheme { val coins = remember { mutableIntStateOf(100) } - BetStatusBottomSheetBetDisplayer( - userCoinAmount = coins, - onParticipate = {} - ).DisplayBet(bet) + BetStatusBottomSheetBetDisplayer {}.DisplayBet(bet) } } \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInButton.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInButton.kt index 7917058..f6ad5d8 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInButton.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInButton.kt @@ -15,10 +15,11 @@ import fr.iut.alldev.allin.theme.AllInTheme @Composable fun AllInButton( + modifier: Modifier = Modifier, + enabled: Boolean = true, color: Color, text: String, textColor: Color, - modifier: Modifier = Modifier, radius: Dp = 15.dp, onClick: () -> Unit, ) { @@ -26,13 +27,14 @@ fun AllInButton( onClick = onClick, modifier = modifier, radius = radius, - backgroundColor = color + backgroundColor = color, + enabled = enabled ) { Text( text = text, textAlign = TextAlign.Center, style = AllInTheme.typography.h2, - color = textColor, + color = if(enabled) textColor else AllInTheme.themeColors.disabledBorder, fontSize = 20.sp, modifier = Modifier .padding(vertical = 15.dp) @@ -51,6 +53,21 @@ private fun AllInButtonPreview() { textColor = Color.White ) { + } + } +} + +@Preview +@Composable +private fun AllInButtonDisabledPreview() { + AllInTheme { + AllInButton( + color = AllInTheme.colors.allInLoginPurple, + text = "Connexion", + textColor = Color.White, + enabled = false + ) { + } } } \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInSelectionBox.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInSelectionBox.kt index c5be688..d88fd23 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInSelectionBox.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInSelectionBox.kt @@ -6,8 +6,10 @@ import androidx.compose.animation.animateContentSize import androidx.compose.foundation.clickable import androidx.compose.foundation.interaction.MutableInteractionSource import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row +import androidx.compose.foundation.layout.RowScope import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.size @@ -29,6 +31,7 @@ import androidx.compose.ui.graphics.vector.ImageVector import androidx.compose.ui.res.stringResource import androidx.compose.ui.text.font.FontWeight import androidx.compose.ui.tooling.preview.Preview +import androidx.compose.ui.unit.Dp import androidx.compose.ui.unit.dp import fr.iut.alldev.allin.R import fr.iut.alldev.allin.theme.AllInTheme @@ -36,11 +39,11 @@ import fr.iut.alldev.allin.theme.AllInTheme class SelectionElement( val textId: Int, - val imageVector: ImageVector, + val imageVector: ImageVector ) @Composable -fun AllInSelectionLine( +private fun AllInSelectionLine( text: String, iconVector: ImageVector?, modifier: Modifier = Modifier, @@ -91,13 +94,19 @@ fun AllInSelectionLine( fun AllInSelectionBox( modifier: Modifier = Modifier, isOpen: Boolean, + borderWidth: Dp? = null, setIsOpen: (Boolean) -> Unit, selected: SelectionElement?, setSelected: (SelectionElement) -> Unit, elements: List, ) { val interactionSource = remember { MutableInteractionSource() } - AllInCard(modifier.fillMaxWidth()) { + AllInCard( + modifier = modifier.fillMaxWidth(), + radius = 10.dp, + borderWidth = borderWidth, + borderColor = AllInTheme.colors.allInPurple.copy(alpha = .42f) + ) { Column( Modifier.animateContentSize() ) { @@ -154,6 +163,84 @@ private fun AllInSelectionBoxClosedPreview() { } } +@Composable +private fun AllInSelectionLine( + element: @Composable RowScope.() -> Unit, + modifier: Modifier = Modifier, + onClick: () -> Unit, + trailingIcon: ImageVector? = null, + interactionSource: MutableInteractionSource +) { + Row( + modifier = modifier + .fillMaxWidth() + .clickable( + interactionSource = interactionSource, + indication = null, + onClick = onClick + ) + .padding(horizontal = 12.dp, vertical = 10.dp), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.SpaceBetween + ) { + element() + trailingIcon?.let { + Icon( + imageVector = trailingIcon, + contentDescription = null, + tint = AllInTheme.colors.allInPurple, + modifier = Modifier + .size(30.dp) + ) + } + } +} + +@Composable +fun AllInSelectionBox( + modifier: Modifier = Modifier, + isOpen: Boolean, + setIsOpen: (Boolean) -> Unit, + borderWidth: Dp? = null, + selected: (@Composable RowScope.() -> Unit)?, + setSelected: (@Composable RowScope.() -> Unit) -> Unit, + elements: List<@Composable RowScope.() -> Unit>, +) { + val interactionSource = remember { MutableInteractionSource() } + AllInCard( + modifier = modifier.fillMaxWidth(), + radius = 10.dp, + borderWidth = borderWidth, + borderColor = AllInTheme.colors.allInPurple.copy(alpha = .42f) + ) { + Column(Modifier.animateContentSize()) { + AllInSelectionLine( + element = selected ?: { Box { } }, + onClick = { setIsOpen(!isOpen) }, + interactionSource = interactionSource, + trailingIcon = with(Icons.Default) { + if (isOpen) ExpandLess else ExpandMore + } + ) + AnimatedVisibility(isOpen) { + Column { + HorizontalDivider(color = AllInTheme.themeColors.border) + elements.filter { it != selected }.forEach { element -> + AllInSelectionLine( + element = element, + interactionSource = interactionSource, + onClick = { + setSelected(element) + setIsOpen(false) + } + ) + } + } + } + } + } +} + @Preview @Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) @Composable diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextField.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextField.kt index 9382045..c46d777 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextField.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/core/AllInTextField.kt @@ -2,7 +2,6 @@ package fr.iut.alldev.allin.ui.core import android.content.res.Configuration import androidx.compose.foundation.ExperimentalFoundationApi -import androidx.compose.foundation.relocation.BringIntoViewRequester import androidx.compose.foundation.text.KeyboardActions import androidx.compose.foundation.text.KeyboardOptions import androidx.compose.material.icons.Icons @@ -11,35 +10,37 @@ import androidx.compose.material.icons.filled.VisibilityOff import androidx.compose.material3.* import androidx.compose.runtime.* import androidx.compose.ui.Modifier -import androidx.compose.ui.focus.onFocusChanged import androidx.compose.ui.graphics.Color -import androidx.compose.ui.graphics.vector.ImageVector -import androidx.compose.ui.text.TextRange +import androidx.compose.ui.graphics.painter.Painter +import androidx.compose.ui.platform.LocalConfiguration import androidx.compose.ui.text.input.* import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.TextUnit import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp +import androidx.core.os.ConfigurationCompat +import androidx.core.text.isDigitsOnly +import fr.iut.alldev.allin.ext.formatToSimple +import fr.iut.alldev.allin.ext.toFloatOrNull +import fr.iut.alldev.allin.ext.verifyIsFloat import fr.iut.alldev.allin.theme.AllInTheme -import kotlinx.coroutines.launch import racra.compose.smooth_corner_rect_library.AbsoluteSmoothCornerShape +import java.util.Locale @OptIn(ExperimentalFoundationApi::class, ExperimentalMaterial3Api::class) @Composable fun AllInTextField( - placeholder: String, - value: String, modifier: Modifier = Modifier, + placeholder: String? = null, + value: String, maxChar: Int? = null, enabled: Boolean = true, - trailingIcon: ImageVector? = null, - trailingContent: @Composable (() -> Unit)? = null, + trailingIcon: Painter? = null, + trailingContent: @Composable() (() -> Unit)? = null, placeholderFontSize: TextUnit = 18.sp, multiLine: Boolean = false, - onValueChange: (String) -> Unit, errorText: String? = null, - bringIntoViewRequester: BringIntoViewRequester, visualTransformation: VisualTransformation = VisualTransformation.None, keyboardType: KeyboardType = KeyboardType.Text, imeAction: ImeAction = ImeAction.Default, @@ -48,58 +49,38 @@ fun AllInTextField( containerColor: Color = AllInTheme.themeColors.background, textColor: Color = AllInTheme.themeColors.onMainSurface, placeholderColor: Color = AllInTheme.themeColors.onBackground2, + onValueChange: (String) -> Unit, ) { - val scope = rememberCoroutineScope() - var hasFocus by remember { mutableStateOf(false) } - - var textFieldValue by remember { - mutableStateOf(TextFieldValue(text = value, selection = TextRange(value.length))) - } - - LaunchedEffect(key1 = value, block = { - textFieldValue = TextFieldValue( - text = value, - selection = textFieldValue.selection - ) - }) - OutlinedTextField( - value = textFieldValue, + value = value, isError = errorText != null, - modifier = modifier - .onFocusChanged { - hasFocus = it.hasFocus - if (it.isFocused) { - scope.launch { - bringIntoViewRequester.bringIntoView() - } - } - }, + modifier = modifier, supportingText = errorText?.let { { AllInErrorLine(text = it) } }, visualTransformation = visualTransformation, singleLine = !multiLine, onValueChange = { - if (maxChar == null || it.text.length <= maxChar) { - textFieldValue = it - onValueChange(it.text) + if (maxChar == null || it.length <= maxChar) { + onValueChange(it) } }, - placeholder = { - Text( - text = placeholder, - fontSize = placeholderFontSize, - style = AllInTheme.typography.p1, - color = placeholderColor, - maxLines = if (multiLine) 3 else 1, - overflow = TextOverflow.Ellipsis - ) + placeholder = placeholder?.let { + { + Text( + text = placeholder, + fontSize = placeholderFontSize, + style = AllInTheme.typography.p1, + color = placeholderColor, + maxLines = if (multiLine) 3 else 1, + overflow = TextOverflow.Ellipsis + ) + } }, trailingIcon = trailingContent ?: trailingIcon?.let { @Composable { Icon( - imageVector = it, + painter = it, contentDescription = null, tint = AllInTheme.colors.allInLightGrey300 ) @@ -135,22 +116,13 @@ fun AllInPasswordField( keyboardActions: KeyboardActions = KeyboardActions.Default, errorText: String? = null, onValueChange: (String) -> Unit, - bringIntoViewRequester: BringIntoViewRequester, isHiddenByDefault: Boolean = true, ) { - var hidden by remember { - mutableStateOf(isHiddenByDefault) - } + var hidden by remember { mutableStateOf(isHiddenByDefault) } AllInTextField( - modifier = modifier, - errorText = errorText, placeholder = placeholder, - imeAction = imeAction, - keyboardActions = keyboardActions, - visualTransformation = if (hidden) PasswordVisualTransformation() else VisualTransformation.None, value = value, - onValueChange = onValueChange, - bringIntoViewRequester = bringIntoViewRequester, + modifier = modifier, trailingContent = { IconButton( onClick = { hidden = !hidden } @@ -162,10 +134,73 @@ fun AllInPasswordField( ) } }, - keyboardType = keyboardType + onValueChange = onValueChange, + errorText = errorText, + visualTransformation = if (hidden) PasswordVisualTransformation() else VisualTransformation.None, + keyboardType = keyboardType, + imeAction = imeAction, + keyboardActions = keyboardActions ) } +@Composable +fun AllInFloatTextfield( + modifier: Modifier = Modifier, + value: Float?, + setValue: (Float?) -> Unit +) { + val configuration = LocalConfiguration.current + val locale = remember { + ConfigurationCompat.getLocales(configuration).get(0) ?: Locale.getDefault() + } + var stringValue by remember(value) { mutableStateOf(value?.formatToSimple(locale) ?: "") } + + AllInTextField( + value = stringValue, + modifier = modifier, + maxChar = 5, + keyboardType = KeyboardType.Number + ) { + it.verifyIsFloat(locale)?.let { + stringValue = it + if (it.isNotEmpty()) { + if (it.lastOrNull() !in setOf(',', '.')) { + it.toFloatOrNull(locale)?.let { + setValue(it) + } + } + } else setValue(null) + } + } +} + +@Composable +fun AllInIntTextField( + modifier: Modifier = Modifier, + placeholder: String? = null, + maxChar: Int? = 3, + value: Int?, + trailingIcon: Painter? = null, + setValue: (Int?) -> Unit +) { + AllInTextField( + value = value?.toString() ?: "", + placeholder = placeholder, + modifier = modifier, + maxChar = maxChar, + trailingIcon = trailingIcon, + keyboardType = KeyboardType.NumberPassword + ) { + if (it.isEmpty()) setValue(null) + else if (it.isDigitsOnly()) { + it.toIntOrNull()?.let { + setValue(it) + } + } + } +} + + @OptIn(ExperimentalFoundationApi::class) @Preview @Composable @@ -174,8 +209,7 @@ private fun AllInTextFieldPlaceholderPreview() { AllInTextField( placeholder = "Email", value = "", - onValueChange = { }, - bringIntoViewRequester = BringIntoViewRequester() + onValueChange = { } ) } } @@ -190,8 +224,7 @@ private fun AllInTextFieldValuePreview() { AllInTextField( placeholder = "Email", value = "JohnDoe@mail.com", - onValueChange = { }, - bringIntoViewRequester = BringIntoViewRequester() + onValueChange = { } ) } } @@ -204,9 +237,8 @@ private fun AllInTextFieldErrorPreview() { AllInTextField( placeholder = "Email", value = "JohnDoe@mail.com", - errorText = "This is an error.", onValueChange = { }, - bringIntoViewRequester = BringIntoViewRequester() + errorText = "This is an error." ) } } @@ -220,13 +252,11 @@ private fun AllInTextFieldPasswordPreview() { AllInPasswordField( placeholder = "Password", value = value, - onValueChange = setValue, - bringIntoViewRequester = BringIntoViewRequester() + onValueChange = setValue ) } } -@OptIn(ExperimentalFoundationApi::class) @Preview @Composable private fun AllInTextFieldMultilinePreview() { @@ -234,9 +264,8 @@ private fun AllInTextFieldMultilinePreview() { AllInTextField( placeholder = "David sera il absent le Lundi matin en cours ?", value = "", - onValueChange = { }, multiLine = true, - bringIntoViewRequester = BringIntoViewRequester() + onValueChange = { } ) } } \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/login/LoginScreen.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/login/LoginScreen.kt index 1b9bd80..87c04bb 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/login/LoginScreen.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/login/LoginScreen.kt @@ -1,6 +1,5 @@ package fr.iut.alldev.allin.ui.login -import androidx.compose.foundation.ExperimentalFoundationApi import androidx.compose.foundation.background import androidx.compose.foundation.layout.Arrangement import androidx.compose.foundation.layout.Box @@ -11,12 +10,10 @@ import androidx.compose.foundation.layout.fillMaxSize import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.padding -import androidx.compose.foundation.relocation.BringIntoViewRequester import androidx.compose.foundation.rememberScrollState import androidx.compose.foundation.text.ClickableText import androidx.compose.foundation.text.KeyboardActions import androidx.compose.foundation.verticalScroll -import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.Text import androidx.compose.runtime.Composable import androidx.compose.runtime.getValue @@ -42,7 +39,6 @@ import fr.iut.alldev.allin.ui.core.AllInLoading import fr.iut.alldev.allin.ui.core.AllInPasswordField import fr.iut.alldev.allin.ui.core.AllInTextField -@OptIn(ExperimentalFoundationApi::class, ExperimentalMaterial3Api::class) @Composable fun LoginScreen( navigateToDashboard: () -> Unit, @@ -51,7 +47,6 @@ fun LoginScreen( ) { val focusManager = LocalFocusManager.current - val bringIntoViewRequester = BringIntoViewRequester() val loading by remember { loginViewModel.loading } var hasLoginError by remember { loginViewModel.hasError } @@ -102,22 +97,20 @@ fun LoginScreen( verticalArrangement = Arrangement.spacedBy(20.dp) ) { AllInTextField( - modifier = Modifier.fillMaxWidth(), placeholder = stringResource(id = R.string.username), value = username, + modifier = Modifier.fillMaxWidth(), onValueChange = setUsername, - bringIntoViewRequester = bringIntoViewRequester, imeAction = ImeAction.Next, keyboardActions = keyboardActions ) AllInPasswordField( - modifier = Modifier.fillMaxWidth(), placeholder = stringResource(id = R.string.password), value = password, - onValueChange = setPassword, - bringIntoViewRequester = bringIntoViewRequester, + modifier = Modifier.fillMaxWidth(), imeAction = ImeAction.Done, - keyboardActions = keyboardActions + keyboardActions = keyboardActions, + onValueChange = setPassword ) } ClickableText( diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt index 1ba9b8f..7f57f2e 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt @@ -70,14 +70,15 @@ fun MainScreen( val (selectedBet, setSelectedBet) = remember { mainViewModel.selectedBet } val (wonBet, setWonBet) = remember { mainViewModel.wonBet } val (statusVisibility, sheetBackVisibility, setStatusVisibility) = rememberBetStatusVisibilities() - val (displayResult, setDisplayResult ) = remember{ mutableStateOf(true) } + val (participateSheetVisibility, setParticipateSheetVisibility) = remember { + mutableStateOf(false) + } + + val (displayResult, setDisplayResult) = remember { mutableStateOf(true) } val betStatusDisplayer = remember { BetStatusBottomSheetBetDisplayer( - userCoinAmount = currentUser.userCoins, - onParticipate = { - mainViewModel.participateToBet(it) - } + openParticipateSheet = { setParticipateSheetVisibility(true) } ) } @@ -152,7 +153,7 @@ fun MainScreen( navController = navController, selectBet = { bet, participate -> setSelectedBet(bet) - betStatusDisplayer.participateBottomSheetVisibility.value = participate + setParticipateSheetVisibility(participate) setStatusVisibility(true) }, setLoading = { loading = it }, @@ -180,11 +181,14 @@ fun MainScreen( state = statusBottomSheetState, sheetVisibility = statusVisibility.value, sheetBackVisibility = sheetBackVisibility.value, - onDismiss = { - setStatusVisibility(false) - }, + onDismiss = { setStatusVisibility(false) }, bet = selectedBet, - displayBet = { betStatusDisplayer.DisplayBet(it) } + paddingValues = betStatusDisplayer.paddingValues.value, + displayBet = { betStatusDisplayer.DisplayBet(it) }, + userCoinAmount = mainViewModel.currentUserState.userCoins, + onParticipate = { mainViewModel.participateToBet(it) }, + participateSheetVisibility = participateSheetVisibility, + setParticipateSheetVisibility = setParticipateSheetVisibility ) AllInLoading(visible = loading) BackHandler( diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt index 8287d8c..aac1fcf 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt @@ -62,7 +62,7 @@ class MainViewModel @Inject constructor( viewModelScope.launch { withContext(Dispatchers.IO) { loading.value = true - currentUserState.userCoins.intValue += 50 + currentUserState.userCoins.intValue -= stake Thread.sleep(1000) loading.value = false } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt index 304f569..dabcded 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt @@ -9,7 +9,7 @@ import fr.iut.alldev.allin.data.model.bet.MatchBet import fr.iut.alldev.allin.data.model.bet.YesNoBet import java.time.ZonedDateTime -class BetPreviewProvider: PreviewParameterProvider { +class BetPreviewProvider : PreviewParameterProvider { override val values = sequenceOf( YesNoBet( theme = "Theme", @@ -39,7 +39,7 @@ class BetPreviewProvider: PreviewParameterProvider { isPublic = true, betStatus = BetStatus.Finished(BetFinishedStatus.WON), creator = "creator", - possibleAnswers = setOf( + possibleAnswers = listOf( "Answer 1", "Answer 2", "Answer 3", diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt index becf11a..fcc5adb 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt @@ -40,7 +40,7 @@ class BetWithStatusPreviewProvider : PreviewParameterProvider { isPublic = true, betStatus = status, creator = "creator", - possibleAnswers = setOf( + possibleAnswers = listOf( "Answer 1", "Answer 2", "Answer 3", diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/register/RegisterScreen.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/register/RegisterScreen.kt index 8a5f27b..a00754b 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/register/RegisterScreen.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/register/RegisterScreen.kt @@ -2,7 +2,6 @@ package fr.iut.alldev.allin.ui.register import androidx.compose.foundation.* import androidx.compose.foundation.layout.* -import androidx.compose.foundation.relocation.BringIntoViewRequester import androidx.compose.foundation.text.ClickableText import androidx.compose.foundation.text.KeyboardActions import androidx.compose.material3.Text @@ -49,7 +48,6 @@ fun RegisterScreen( val (password, setPassword) = remember { registerViewModel.password } val (passwordValidation, setPasswordValidation) = remember { registerViewModel.passwordValidation } - val bringIntoViewRequester = remember { BringIntoViewRequester() } val scrollState = rememberScrollState() val usernameFieldName = stringResource(id = R.string.username) @@ -117,46 +115,42 @@ fun RegisterScreen( verticalArrangement = Arrangement.spacedBy(20.dp) ) { AllInTextField( - modifier = Modifier.fillMaxWidth(), placeholder = usernameFieldName, value = username, - onValueChange = setUsername, + modifier = Modifier.fillMaxWidth(), maxChar = 20, + onValueChange = setUsername, errorText = usernameError.errorResource(), - bringIntoViewRequester = bringIntoViewRequester, imeAction = ImeAction.Next, keyboardActions = keyboardActions ) AllInTextField( - modifier = Modifier.fillMaxWidth(), placeholder = emailFieldName, value = email, + modifier = Modifier.fillMaxWidth(), onValueChange = setEmail, errorText = emailError.errorResource(), keyboardType = KeyboardType.Email, - bringIntoViewRequester = bringIntoViewRequester, imeAction = ImeAction.Next, keyboardActions = keyboardActions ) AllInPasswordField( - modifier = Modifier.fillMaxWidth(), placeholder = passwordFieldName, value = password, - errorText = passwordError.errorResource(), - onValueChange = setPassword, - bringIntoViewRequester = bringIntoViewRequester, + modifier = Modifier.fillMaxWidth(), imeAction = ImeAction.Next, - keyboardActions = keyboardActions + keyboardActions = keyboardActions, + errorText = passwordError.errorResource(), + onValueChange = setPassword ) AllInPasswordField( - modifier = Modifier.fillMaxWidth(), placeholder = stringResource(id = R.string.confirm_password), value = passwordValidation, - errorText = passwordValidationError.errorResource(), - onValueChange = setPasswordValidation, - bringIntoViewRequester = bringIntoViewRequester, + modifier = Modifier.fillMaxWidth(), imeAction = ImeAction.Done, - keyboardActions = keyboardActions + keyboardActions = keyboardActions, + errorText = passwordValidationError.errorResource(), + onValueChange = setPasswordValidation ) } } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt b/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt index deaf6f9..be89c05 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt @@ -17,11 +17,11 @@ interface BetDisplayer { } @Composable - fun DisplayYesNoBet(b: YesNoBet) + fun DisplayYesNoBet(bet: YesNoBet) @Composable - fun DisplayMatchBet(b: MatchBet) + fun DisplayMatchBet(bet: MatchBet) @Composable - fun DisplayCustomBet(b: CustomBet) + fun DisplayCustomBet(bet: CustomBet) } \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/api/MockAllInApi.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/api/MockAllInApi.kt new file mode 100644 index 0000000..4b61b9b --- /dev/null +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/api/MockAllInApi.kt @@ -0,0 +1,96 @@ +package fr.iut.alldev.allin.data.api + +import fr.iut.alldev.allin.data.api.interceptors.AllInAPIException +import fr.iut.alldev.allin.data.api.model.CheckUser +import fr.iut.alldev.allin.data.api.model.RequestBet +import fr.iut.alldev.allin.data.api.model.RequestUser +import fr.iut.alldev.allin.data.api.model.ResponseBet +import fr.iut.alldev.allin.data.api.model.ResponseUser +import fr.iut.alldev.allin.data.model.bet.NO_VALUE +import fr.iut.alldev.allin.data.model.bet.YES_VALUE +import java.time.ZonedDateTime +import java.util.UUID + +class MockAllInApi : AllInApi { + override suspend fun login(body: CheckUser): ResponseUser { + return users.find { it.first.username == body.login && it.second == body.password }?.first + ?: throw AllInAPIException("Invalid login/password.") + } + + override suspend fun login(token: String): ResponseUser { + return users.find { it.first.token == token }?.first + ?: throw AllInAPIException("Invalid token") + } + + override suspend fun register(body: RequestUser): ResponseUser { + val response = ResponseUser( + id = UUID.randomUUID().toString(), + username = body.username, + email = body.email, + nbCoins = body.nbCoins, + token = "${body.username} ${users.size}" + ) to body.password + users.add(response) + return response.first + } + + override suspend fun createBet(token: String, body: RequestBet) { + mockBets.add( + ResponseBet( + id = UUID.randomUUID().toString(), + theme = body.theme, + sentenceBet = body.sentenceBet, + endRegistration = body.endRegistration, + endBet = body.endBet, + isPrivate = body.isPrivate, + response = body.response, + createdBy = "" + ) + ) + } + + override suspend fun getAllBets(): List = mockBets.toList() +} + +private val users = mutableListOf( + ResponseUser( + id = "UUID 1", + username = "User 1", + email = "john@doe.fr", + nbCoins = 250, + token = "token 1" + ) to "psswrd" +) + +private val mockBets = mutableListOf( + ResponseBet( + id = "UUID1", + theme = "Études", + sentenceBet = "Dave va arriver en retard demain matin ?", + endRegistration = ZonedDateTime.now().plusDays(3), + endBet = ZonedDateTime.now().plusDays(4), + isPrivate = false, + response = listOf(YES_VALUE, NO_VALUE), + createdBy = "Armure" + ), + ResponseBet( + id = "UUID2", + theme = "Études", + sentenceBet = "Dave va arriver en retard demain matin ?", + endRegistration = ZonedDateTime.now().plusDays(3), + endBet = ZonedDateTime.now().plusDays(4), + isPrivate = false, + response = listOf("Answer 1", "Answer 2", "Answer 3", "Answer 4"), + createdBy = "User 2" + ), + ResponseBet( + id = "UUID3", + theme = "Sport", + sentenceBet = "Nouveau record du monde ?", + endRegistration = ZonedDateTime.now().plusDays(3), + endBet = ZonedDateTime.now().plusDays(4), + isPrivate = false, + response = listOf(YES_VALUE, NO_VALUE), + createdBy = "Armure" + ) +) \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt index c5da50a..4eca5f1 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt @@ -4,6 +4,8 @@ import androidx.annotation.Keep import fr.iut.alldev.allin.data.model.bet.Bet import fr.iut.alldev.allin.data.model.bet.BetStatus import fr.iut.alldev.allin.data.model.bet.CustomBet +import fr.iut.alldev.allin.data.model.bet.NO_VALUE +import fr.iut.alldev.allin.data.model.bet.YES_VALUE import fr.iut.alldev.allin.data.model.bet.YesNoBet import fr.iut.alldev.allin.data.serialization.SimpleDateSerializer import kotlinx.serialization.Serializable @@ -12,7 +14,7 @@ import java.time.ZonedDateTime @Keep @Serializable data class ResponseBet( - val id: Int?, + val id: String?, val theme: String, val sentenceBet: String, @Serializable(SimpleDateSerializer::class) val endRegistration: ZonedDateTime, @@ -22,7 +24,7 @@ data class ResponseBet( val createdBy: String ) { fun toBet(): Bet { - if (response.toSet() == setOf("Yes", "No")) { + if (response.toSet() == setOf(YES_VALUE, NO_VALUE)) { return YesNoBet( theme = theme, phrase = sentenceBet, @@ -41,7 +43,7 @@ data class ResponseBet( isPublic = !isPrivate, betStatus = BetStatus.Waiting, creator = createdBy, - possibleAnswers = response.toSet() + possibleAnswers = response ) } } diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiUser.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiUser.kt index 37af616..79d1681 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiUser.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiUser.kt @@ -16,15 +16,16 @@ data class RequestUser( @Keep @Serializable data class ResponseUser( + val id: String, val username: String, val email: String, var nbCoins: Int, var token: String? = null, ) { fun toUser() = User( + id = id, username = username, email = email, - id = "", coins = nbCoins ) } diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/di/ApiModule.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/di/ApiModule.kt index 3883391..50c387a 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/di/ApiModule.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/di/ApiModule.kt @@ -5,18 +5,25 @@ import dagger.Provides import dagger.hilt.InstallIn import dagger.hilt.components.SingletonComponent import fr.iut.alldev.allin.data.api.AllInApi +import fr.iut.alldev.allin.data.api.MockAllInApi import fr.iut.alldev.allin.data.di.NetworkModule.createRetrofit import okhttp3.HttpUrl import okhttp3.OkHttpClient import javax.inject.Singleton +const val mock = true + @Module @InstallIn(SingletonComponent::class) class ApiModule { @Provides @Singleton fun provideAllInApi(@AllInUrl url: HttpUrl, okHttpClient: OkHttpClient): AllInApi { - val retrofit = createRetrofit(url = url, okHttpClient = okHttpClient) - return retrofit.create(AllInApi::class.java) + return if (mock) { + MockAllInApi() + } else { + val retrofit = createRetrofit(url = url, okHttpClient = okHttpClient) + retrofit.create(AllInApi::class.java) + } } } \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt index 21684a7..cc1910a 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt @@ -4,7 +4,7 @@ import fr.iut.alldev.allin.data.api.model.RequestBet import java.time.ZonedDateTime sealed class Bet( - open val id: Int? = null, + open val id: String? = null, open val creator: String, open val theme: String, open val phrase: String, diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetFactory.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetFactory.kt index f48a5d3..c194a30 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetFactory.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetFactory.kt @@ -14,7 +14,7 @@ class BetFactory { isPublic: Boolean, nameTeam1: String = "", nameTeam2: String = "", - possibleAnswers: Set = emptySet(), + possibleAnswers: List = emptyList(), ): Bet = when (betType) { diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/CustomBet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/CustomBet.kt index 4a8320d..8af1e5e 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/CustomBet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/CustomBet.kt @@ -3,7 +3,7 @@ package fr.iut.alldev.allin.data.model.bet import java.time.ZonedDateTime data class CustomBet( - override val id: Int? = null, + override val id: String? = null, override val creator: String, override val theme: String, override val phrase: String, @@ -11,7 +11,7 @@ data class CustomBet( override val endBetDate: ZonedDateTime, override val isPublic: Boolean, override val betStatus: BetStatus, - val possibleAnswers: Set, + val possibleAnswers: List ) : Bet( id, creator, @@ -22,5 +22,5 @@ data class CustomBet( isPublic, betStatus ) { - override fun getResponses(): List = possibleAnswers.toList() + override fun getResponses(): List = possibleAnswers } diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/MatchBet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/MatchBet.kt index e0a4211..4e96674 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/MatchBet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/MatchBet.kt @@ -3,7 +3,7 @@ package fr.iut.alldev.allin.data.model.bet import java.time.ZonedDateTime data class MatchBet( - override val id: Int? = null, + override val id: String? = null, override val creator: String, override val theme: String, override val phrase: String, @@ -12,7 +12,7 @@ data class MatchBet( override val isPublic: Boolean, override val betStatus: BetStatus, val nameTeam1: String, - val nameTeam2: String, + val nameTeam2: String ) : Bet( id, creator, diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/YesNoBet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/YesNoBet.kt index 8252dab..2c57d4e 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/YesNoBet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/YesNoBet.kt @@ -2,15 +2,18 @@ package fr.iut.alldev.allin.data.model.bet import java.time.ZonedDateTime +const val YES_VALUE = "Yes" +const val NO_VALUE = "No" + data class YesNoBet( - override val id: Int? = null, + override val id: String? = null, override val creator: String, override val theme: String, override val phrase: String, override val endRegisterDate: ZonedDateTime, override val endBetDate: ZonedDateTime, override val isPublic: Boolean, - override val betStatus: BetStatus, + override val betStatus: BetStatus ) : Bet( id, creator, @@ -21,5 +24,5 @@ data class YesNoBet( isPublic, betStatus ) { - override fun getResponses(): List = listOf("Yes", "No") + override fun getResponses(): List = listOf(YES_VALUE, NO_VALUE) } \ No newline at end of file From 7c643ebe74f6262552c59998604a8a207498a3bf Mon Sep 17 00:00:00 2001 From: "arthur.valin" Date: Tue, 23 Jan 2024 21:39:15 +0100 Subject: [PATCH 3/3] BetDetail and Participation --- .../iut/alldev/allin/di/CurrentUserModule.kt | 4 +- .../java/fr/iut/alldev/allin/theme/Icons.kt | 2 +- .../ui/betCreation/BetCreationViewModel.kt | 1 + .../tabs/BetCreationScreenQuestionTab.kt | 10 +- .../ui/betResult/BetResultBottomSheet.kt | 1 + .../ui/betStatus/BetStatusBottomSheet.kt | 29 +-- .../BetStatusParticipationAnswers.kt | 146 +++++++++----- .../BetStatusParticipationBottomSheet.kt | 7 +- .../ui/betStatus/components/YesNoStarBar.kt | 24 ++- .../vo/BetStatusBottomSheetBetDisplayer.kt | 178 ++++++++++++++---- .../fr/iut/alldev/allin/ui/main/MainScreen.kt | 8 +- .../iut/alldev/allin/ui/main/MainViewModel.kt | 47 +++-- .../ui/preview/BetDetailPreviewProvider.kt | 58 ++++++ .../allin/ui/preview/BetPreviewProvider.kt | 3 + .../preview/BetWithStatusPreviewProvider.kt | 3 + .../java/fr/iut/alldev/allin/utils/Tuples.kt | 12 -- .../iut/alldev/allin/vo/bet/BetDisplayer.kt | 18 +- src/app/src/main/res/values-fr/strings.xml | 1 + src/app/src/main/res/values/strings.xml | 1 + .../fr/iut/alldev/allin/data/api/AllInApi.kt | 13 ++ .../iut/alldev/allin/data/api/MockAllInApi.kt | 157 ++++++++++++++- .../data/api/interceptors/ErrorInterceptor.kt | 5 +- .../iut/alldev/allin/data/api/model/ApiBet.kt | 52 ++++- .../allin/data/api/model/ApiParticipation.kt | 31 +++ .../alldev/allin/data/api/model/ApiUser.kt | 9 +- .../fr/iut/alldev/allin/data/di/ApiModule.kt | 2 +- .../iut/alldev/allin/data/di/NetworkModule.kt | 2 +- .../fr/iut/alldev/allin/data/model/User.kt | 8 +- .../fr/iut/alldev/allin/data/model/bet/Bet.kt | 3 +- .../alldev/allin/data/model/bet/BetFactory.kt | 4 + .../alldev/allin/data/model/bet/CustomBet.kt | 2 +- .../alldev/allin/data/model/bet/MatchBet.kt | 2 +- .../allin/data/model/bet/Participation.kt | 17 ++ .../alldev/allin/data/model/bet/YesNoBet.kt | 2 +- .../data/model/bet/vo/BetAnswerDetail.kt | 9 + .../allin/data/model/bet/vo/BetDetail.kt | 14 ++ .../allin/data/model/bet/vo/BetResult.kt | 10 + .../allin/data/repository/BetRepository.kt | 4 + .../allin/data/repository/UserRepository.kt | 11 +- .../data/repository/impl/BetRepositoryImpl.kt | 22 ++- .../repository/impl/UserRepositoryImpl.kt | 6 +- .../serialization/ZonedDateTimeSerializer.kt | 29 +-- 42 files changed, 748 insertions(+), 219 deletions(-) create mode 100644 src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetDetailPreviewProvider.kt delete mode 100644 src/app/src/main/java/fr/iut/alldev/allin/utils/Tuples.kt create mode 100644 src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiParticipation.kt create mode 100644 src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Participation.kt create mode 100644 src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetAnswerDetail.kt create mode 100644 src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetDetail.kt create mode 100644 src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetResult.kt diff --git a/src/app/src/main/java/fr/iut/alldev/allin/di/CurrentUserModule.kt b/src/app/src/main/java/fr/iut/alldev/allin/di/CurrentUserModule.kt index 2010974..fee0dc8 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/di/CurrentUserModule.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/di/CurrentUserModule.kt @@ -16,7 +16,5 @@ annotation class AllInCurrentUser internal object CurrentUserModule { @AllInCurrentUser @Provides - fun provideUser( - userRepository: UserRepository - ) = userRepository.currentUser + fun provideUser(userRepository: UserRepository) = userRepository.currentUser } \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/theme/Icons.kt b/src/app/src/main/java/fr/iut/alldev/allin/theme/Icons.kt index 819c5b5..8382348 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/theme/Icons.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/theme/Icons.kt @@ -9,7 +9,7 @@ import androidx.compose.ui.graphics.painter.Painter @Immutable data class AllInIcons( - val allCoins: @Composable ()->Painter, + val allCoins: @Composable () -> Painter, ) internal val LocalIcons = staticCompositionLocalOf { diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/BetCreationViewModel.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/BetCreationViewModel.kt index 71d3aae..5e420ea 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/BetCreationViewModel.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/BetCreationViewModel.kt @@ -110,6 +110,7 @@ class BetCreationViewModel @Inject constructor( if (!hasError.value) { try { val bet = BetFactory.createBet( + id = "", betType = selectedBetType.value, theme = theme.value, phrase = phrase.value, diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/BetCreationScreenQuestionTab.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/BetCreationScreenQuestionTab.kt index 5edafd5..1065e7e 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/BetCreationScreenQuestionTab.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betCreation/tabs/BetCreationScreenQuestionTab.kt @@ -1,10 +1,10 @@ package fr.iut.alldev.allin.ui.betCreation.tabs -import androidx.compose.foundation.ExperimentalFoundationApi import androidx.compose.foundation.interaction.MutableInteractionSource -import androidx.compose.foundation.layout.* -import androidx.compose.foundation.relocation.BringIntoViewRequester -import androidx.compose.runtime.* +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.height +import androidx.compose.runtime.Composable import androidx.compose.ui.Modifier import androidx.compose.ui.unit.dp import fr.iut.alldev.allin.data.ext.formatToMediumDate @@ -14,7 +14,6 @@ import fr.iut.alldev.allin.ui.betCreation.tabs.sections.QuestionTabPrivacySectio import fr.iut.alldev.allin.ui.betCreation.tabs.sections.QuestionTabThemePhraseSection import java.time.ZonedDateTime -@OptIn(ExperimentalFoundationApi::class) @Composable fun BetCreationScreenQuestionTab( modifier: Modifier = Modifier, @@ -38,7 +37,6 @@ fun BetCreationScreenQuestionTab( setEndTimeDialog: (Boolean) -> Unit, interactionSource: MutableInteractionSource ) { - val bringIntoViewRequester = remember { BringIntoViewRequester() } Column(modifier) { QuestionTabThemePhraseSection( betTheme = betTheme, diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/BetResultBottomSheet.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/BetResultBottomSheet.kt index 3eebfbe..7fd4eeb 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/BetResultBottomSheet.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betResult/BetResultBottomSheet.kt @@ -154,6 +154,7 @@ private fun BetResultBottomSheetContentPreview() { username = "Pseudo", coinAmount = 3976, bet = YesNoBet( + id = "1", theme = "Theme", phrase = "Phrase", endRegisterDate = ZonedDateTime.now(), diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt index da23df3..7e193fc 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/BetStatusBottomSheet.kt @@ -6,10 +6,11 @@ import androidx.compose.material3.* import androidx.compose.runtime.* import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.Color -import fr.iut.alldev.allin.data.model.bet.Bet import fr.iut.alldev.allin.data.model.bet.BetStatus +import fr.iut.alldev.allin.data.model.bet.vo.BetDetail import fr.iut.alldev.allin.ui.betStatus.components.BetStatusBottomSheetBack import fr.iut.alldev.allin.ui.betStatus.components.BetStatusParticipationBottomSheet +import fr.iut.alldev.allin.ui.betStatus.components.getAnswerFromParticipationIdx import fr.iut.alldev.allin.ui.betStatus.components.getParticipationAnswers import fr.iut.alldev.allin.ui.core.AllInBottomSheet @@ -23,14 +24,14 @@ fun BetStatusBottomSheet( state: SheetState, sheetVisibility: Boolean, sheetBackVisibility: Boolean, - bet: Bet?, + betDetail: BetDetail?, paddingValues: PaddingValues, userCoinAmount: MutableIntState, - onParticipate: (Int) -> Unit, + onParticipate: (stake: Int, response: String) -> Unit, onDismiss: () -> Unit, participateSheetVisibility: Boolean, setParticipateSheetVisibility: (Boolean) -> Unit, - displayBet: @Composable (Bet) -> Unit + displayBet: @Composable (BetDetail) -> Unit ) { AnimatedVisibility( visible = sheetBackVisibility, @@ -41,9 +42,9 @@ fun BetStatusBottomSheet( targetOffsetY = { it } ) ) { - bet?.let { + betDetail?.let { BetStatusBottomSheetBack( - status = it.betStatus + status = it.bet.betStatus ) } } @@ -61,14 +62,15 @@ fun BetStatusBottomSheet( Column( Modifier.fillMaxHeight(SHEET_HEIGHT) ) { - bet?.let { - val elements = bet.getParticipationAnswers() + betDetail?.let { + val elements = betDetail.getParticipationAnswers() displayBet(it) BetStatusParticipationBottomSheet( - sheetVisibility = participateSheetVisibility && bet.betStatus == BetStatus.Waiting && state.hasExpandedState, + sheetVisibility = participateSheetVisibility && betDetail.bet.betStatus == BetStatus.Waiting && state.hasExpandedState, safeBottomPadding = paddingValues.calculateBottomPadding(), - betPhrase = bet.phrase, + odds = betDetail.answers.getOrNull(selectedAnswer)?.odds ?: 1f, + betPhrase = betDetail.bet.phrase, coinAmount = userCoinAmount.intValue, onDismiss = { setParticipateSheetVisibility(false) }, state = rememberModalBottomSheetState(skipPartiallyExpanded = true), @@ -80,8 +82,11 @@ fun BetStatusBottomSheet( enabled = stake != null && (stake ?: 0) <= userCoinAmount.intValue ) { - stake?.let { - onParticipate(it) + stake?.let { stake -> + onParticipate( + stake, + betDetail.bet.getAnswerFromParticipationIdx(selectedAnswer) + ) } } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationAnswers.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationAnswers.kt index fa0511f..735ad70 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationAnswers.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationAnswers.kt @@ -1,82 +1,138 @@ package fr.iut.alldev.allin.ui.betStatus.components import android.content.res.Configuration +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.RowScope import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.padding import androidx.compose.material3.Text - import androidx.compose.runtime.Composable +import androidx.compose.runtime.remember +import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier -import androidx.compose.ui.res.stringResource +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.platform.LocalConfiguration import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.tooling.preview.PreviewParameter +import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.sp -import fr.iut.alldev.allin.R +import androidx.core.os.ConfigurationCompat import fr.iut.alldev.allin.data.model.bet.Bet import fr.iut.alldev.allin.data.model.bet.CustomBet import fr.iut.alldev.allin.data.model.bet.MatchBet import fr.iut.alldev.allin.data.model.bet.NO_VALUE import fr.iut.alldev.allin.data.model.bet.YES_VALUE import fr.iut.alldev.allin.data.model.bet.YesNoBet +import fr.iut.alldev.allin.data.model.bet.vo.BetDetail +import fr.iut.alldev.allin.ext.formatToSimple import fr.iut.alldev.allin.theme.AllInTheme -import fr.iut.alldev.allin.ui.preview.BetPreviewProvider +import fr.iut.alldev.allin.ui.core.AllInCard +import fr.iut.alldev.allin.ui.preview.BetDetailPreviewProvider +import java.util.Locale private val participationAnswerFontSize = 25.sp @Composable -fun Bet.getParticipationAnswers(): List<@Composable RowScope.() -> Unit> = - when (this) { - is CustomBet -> this.possibleAnswers.map { +fun BetDetail.getParticipationAnswers(): List<@Composable RowScope.() -> Unit> { + val configuration = LocalConfiguration.current + val locale = remember { ConfigurationCompat.getLocales(configuration).get(0) ?: Locale.getDefault() } + + return when (this.bet) { + is CustomBet -> (this.bet as CustomBet).possibleAnswers.map { { - Text( - text = it, - color = AllInTheme.colors.allInBlue, - style = AllInTheme.typography.h1, - fontSize = participationAnswerFontSize - ) + this@getParticipationAnswers.getAnswerOfResponse(it)?.let { + ParticipationAnswerLine( + text = it.response, + odds = it.odds, + locale = locale + ) + } } } - is MatchBet -> listOf( - { - Text( - text = this@getParticipationAnswers.nameTeam1, - color = AllInTheme.colors.allInBlue, - style = AllInTheme.typography.h1, - fontSize = participationAnswerFontSize - ) - }, - { - Text( - text = this@getParticipationAnswers.nameTeam2, - color = AllInTheme.colors.allInBarPink, - style = AllInTheme.typography.h1, - fontSize = participationAnswerFontSize - ) + is MatchBet -> buildList { + val bet = (this@getParticipationAnswers.bet as MatchBet) + add { + this@getParticipationAnswers.getAnswerOfResponse(bet.nameTeam1)?.let { + ParticipationAnswerLine( + text = it.response, + odds = it.odds, + locale = locale + ) + } } + add { + this@getParticipationAnswers.getAnswerOfResponse(bet.nameTeam2)?.let { + ParticipationAnswerLine( + text = it.response, + color = AllInTheme.colors.allInBarPink, + odds = it.odds, + locale = locale + ) + } + } + } + + is YesNoBet -> buildList { + add { + this@getParticipationAnswers.getAnswerOfResponse(YES_VALUE)?.let { + ParticipationAnswerLine( + text = it.response, + odds = it.odds, + locale = locale + ) + } + } + add { + this@getParticipationAnswers.getAnswerOfResponse(NO_VALUE)?.let { + ParticipationAnswerLine( + text = it.response, + color = AllInTheme.colors.allInBarPink, + odds = it.odds, + locale = locale + ) + } + } + } + } +} + +@Composable +private fun ParticipationAnswerLine( + text: String, + color: Color = AllInTheme.colors.allInBlue, + locale: Locale, + odds: Float +) { + Row( + modifier = Modifier.fillMaxWidth(), + verticalAlignment = Alignment.CenterVertically, + horizontalArrangement = Arrangement.spacedBy(8.dp) + ) { + Text( + text = text.uppercase(), + color = color, + style = AllInTheme.typography.h1, + fontSize = participationAnswerFontSize ) - is YesNoBet -> listOf( - { - Text( - text = stringResource(id = R.string.Yes).uppercase(), - color = AllInTheme.colors.allInBlue, - style = AllInTheme.typography.h1, - fontSize = participationAnswerFontSize - ) - }, - { + AllInCard( + radius = 50.dp, + backgroundColor = AllInTheme.colors.allInPurple + ) { + Box(Modifier.padding(vertical = 4.dp, horizontal = 8.dp)) { Text( - text = stringResource(id = R.string.No).uppercase(), - color = AllInTheme.colors.allInBarPink, - style = AllInTheme.typography.h1, - fontSize = participationAnswerFontSize + text = "x${odds.formatToSimple(locale)}", + color = AllInTheme.colors.white, + style = AllInTheme.typography.h2 ) } - ) + } } +} fun Bet.getAnswerFromParticipationIdx(idx: Int) = when (this) { @@ -98,7 +154,7 @@ fun Bet.getAnswerFromParticipationIdx(idx: Int) = @Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) @Composable private fun ParticipationAnswersPreview( - @PreviewParameter(BetPreviewProvider::class) bet: Bet, + @PreviewParameter(BetDetailPreviewProvider::class) bet: BetDetail, ) { AllInTheme { Column { diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt index 0b2db92..7892162 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/BetStatusParticipationBottomSheet.kt @@ -24,6 +24,7 @@ import fr.iut.alldev.allin.ui.core.AllInIntTextField import fr.iut.alldev.allin.ui.core.AllInSelectionBox import fr.iut.alldev.allin.ui.core.topbar.AllInTopBarCoinCounter import kotlinx.coroutines.launch +import kotlin.math.roundToInt @OptIn(ExperimentalMaterial3Api::class) @Composable @@ -35,6 +36,7 @@ fun BetStatusParticipationBottomSheet( onDismiss: () -> Unit, state: SheetState, enabled: Boolean, + odds: Float, stake: Int?, setStake: (Int?) -> Unit, elements: List<@Composable RowScope.() -> Unit>, @@ -58,6 +60,7 @@ fun BetStatusParticipationBottomSheet( setElement = setElement, enabled = enabled, stake = stake, + odds = odds, setStake = setStake ) { scope.launch { @@ -76,6 +79,7 @@ private fun ColumnScope.BetStatusParticipationBottomSheetContent( coinAmount: Int, enabled: Boolean, stake: Int?, + odds: Float, setStake: (Int?) -> Unit, selectedElement: (@Composable RowScope.() -> Unit)?, elements: List<@Composable RowScope.() -> Unit>, @@ -150,7 +154,7 @@ private fun ColumnScope.BetStatusParticipationBottomSheetContent( color = AllInTheme.themeColors.onBackground ) AllInCoinCount( - amount = 121, + amount = stake?.let { (it + (it * odds)).roundToInt() } ?: 0, color = AllInTheme.themeColors.onBackground ) } @@ -181,6 +185,7 @@ private fun BetStatusParticipationBottomSheetContentPreview() { selectedElement = null, enabled = true, stake = 123, + odds = 0.42f, setStake = {} ) } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoStarBar.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoStarBar.kt index 5abafbd..1aad42e 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoStarBar.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/components/YesNoStarBar.kt @@ -4,27 +4,27 @@ import androidx.compose.foundation.layout.* import androidx.compose.material3.Text import androidx.compose.runtime.Composable import androidx.compose.ui.Modifier -import androidx.compose.ui.res.stringResource import androidx.compose.ui.text.font.FontStyle import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.tooling.preview.PreviewParameter import androidx.compose.ui.tooling.preview.PreviewParameterProvider import androidx.compose.ui.unit.sp -import fr.iut.alldev.allin.R import fr.iut.alldev.allin.data.ext.toPercentageString import fr.iut.alldev.allin.theme.AllInTheme import fr.iut.alldev.allin.ui.core.PercentagePositionnedElement import fr.iut.alldev.allin.ui.core.StatBar @Composable -fun YesNoStatBar( - yesPercentage: Float, +fun BinaryStatBar( + response1Percentage: Float, + response1: String, + response2: String, modifier: Modifier = Modifier, ) { Column(modifier) { Row { Text( - text = stringResource(id = R.string.Yes).uppercase(), + text = response1, color = AllInTheme.colors.allInBlue, style = AllInTheme.typography.h1, fontStyle = FontStyle.Italic, @@ -32,19 +32,19 @@ fun YesNoStatBar( modifier = Modifier.weight(1f) ) Text( - text = stringResource(id = R.string.No).uppercase(), + text = response2, style = AllInTheme.typography.h1, fontStyle = FontStyle.Italic, fontSize = 30.sp, color = AllInTheme.colors.allInBarPink ) } - StatBar(percentage = yesPercentage) + StatBar(percentage = response1Percentage) PercentagePositionnedElement( - percentage = yesPercentage + percentage = response1Percentage ) { Text( - text = yesPercentage.toPercentageString(), + text = response1Percentage.toPercentageString(), style = AllInTheme.typography.sm1, color = AllInTheme.colors.allInBarPurple ) @@ -64,6 +64,10 @@ private fun YesNoStatBarPreview( @PreviewParameter(YesNoStatBarPreviewProvider::class) percentage: Float, ) { AllInTheme { - YesNoStatBar(percentage) + BinaryStatBar( + percentage, + "Answer 1", + "Answer 2" + ) } } \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/vo/BetStatusBottomSheetBetDisplayer.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/vo/BetStatusBottomSheetBetDisplayer.kt index 4c9a268..e316c59 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/vo/BetStatusBottomSheetBetDisplayer.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/betStatus/vo/BetStatusBottomSheetBetDisplayer.kt @@ -3,6 +3,8 @@ package fr.iut.alldev.allin.ui.betStatus.vo import android.content.res.Configuration import androidx.compose.foundation.background import androidx.compose.foundation.layout.* +import androidx.compose.foundation.lazy.LazyColumn +import androidx.compose.foundation.lazy.items import androidx.compose.material.icons.Icons import androidx.compose.material.icons.filled.EmojiEvents import androidx.compose.material.icons.filled.People @@ -13,48 +15,67 @@ import androidx.compose.material3.Text import androidx.compose.runtime.* import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier +import androidx.compose.ui.platform.LocalConfiguration import androidx.compose.ui.res.stringResource +import androidx.compose.ui.text.font.FontWeight +import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.tooling.preview.PreviewParameter import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import androidx.core.os.ConfigurationCompat import fr.iut.alldev.allin.R import fr.iut.alldev.allin.data.ext.formatToMediumDateNoYear import fr.iut.alldev.allin.data.ext.formatToTime -import fr.iut.alldev.allin.data.model.bet.Bet import fr.iut.alldev.allin.data.model.bet.BetStatus -import fr.iut.alldev.allin.data.model.bet.CustomBet import fr.iut.alldev.allin.data.model.bet.MatchBet -import fr.iut.alldev.allin.data.model.bet.YesNoBet +import fr.iut.alldev.allin.data.model.bet.NO_VALUE +import fr.iut.alldev.allin.data.model.bet.YES_VALUE +import fr.iut.alldev.allin.data.model.bet.vo.BetDetail +import fr.iut.alldev.allin.ext.formatToSimple import fr.iut.alldev.allin.ext.getDateEndLabelId import fr.iut.alldev.allin.ext.getDateStartLabelId import fr.iut.alldev.allin.theme.AllInTheme import fr.iut.alldev.allin.ui.betStatus.components.BetStatusWinner +import fr.iut.alldev.allin.ui.betStatus.components.BinaryStatBar import fr.iut.alldev.allin.ui.betStatus.components.YesNoDetailsLine -import fr.iut.alldev.allin.ui.betStatus.components.YesNoStatBar +import fr.iut.alldev.allin.ui.core.AllInCoinCount import fr.iut.alldev.allin.ui.core.AllInDetailsDrawer +import fr.iut.alldev.allin.ui.core.ProfilePicture import fr.iut.alldev.allin.ui.core.RainbowButton import fr.iut.alldev.allin.ui.core.bet.BetDateTimeRow import fr.iut.alldev.allin.ui.core.bet.BetTitleHeader -import fr.iut.alldev.allin.ui.preview.BetWithStatusPreviewProvider +import fr.iut.alldev.allin.ui.preview.BetDetailPreviewProvider import fr.iut.alldev.allin.vo.bet.BetDisplayer +import java.util.Locale class BetStatusBottomSheetBetDisplayer( val openParticipateSheet: () -> Unit ) : BetDisplayer { val paddingValues = mutableStateOf(PaddingValues()) - @OptIn(ExperimentalMaterial3Api::class) @Composable - override fun DisplayYesNoBet(bet: YesNoBet) { + private fun DisplayBinaryBet( + betDetail: BetDetail, + response1: String, + response2: String, + response1Display: String = response1, + response2Display: String = response2 + ) { val safeBottomPadding = paddingValues.value.calculateBottomPadding() + val configuration = LocalConfiguration.current + val locale = remember { ConfigurationCompat.getLocales(configuration).get(0) ?: Locale.getDefault() } + + val response1Answer = remember { betDetail.getAnswerOfResponse(response1) } + val response2Answer = remember { betDetail.getAnswerOfResponse(response2) } Box(Modifier.padding(bottom = safeBottomPadding)) { Column { Column(Modifier.padding(horizontal = 20.dp)) { BetTitleHeader( - title = bet.phrase, - category = bet.theme, - creator = bet.creator, + title = betDetail.bet.phrase, + category = betDetail.bet.theme, + creator = betDetail.bet.creator, modifier = Modifier.fillMaxWidth() ) Spacer(modifier = Modifier.height(20.dp)) @@ -62,24 +83,24 @@ class BetStatusBottomSheetBetDisplayer( horizontalAlignment = Alignment.End ) { BetDateTimeRow( - label = stringResource(id = bet.betStatus.getDateStartLabelId()), - date = bet.endRegisterDate.formatToMediumDateNoYear(), - time = bet.endRegisterDate.formatToTime(), + label = stringResource(id = betDetail.bet.betStatus.getDateStartLabelId()), + date = betDetail.bet.endRegisterDate.formatToMediumDateNoYear(), + time = betDetail.bet.endRegisterDate.formatToTime(), modifier = Modifier.width(IntrinsicSize.Max) ) Spacer(modifier = Modifier.height(15.dp)) BetDateTimeRow( - label = stringResource(id = bet.betStatus.getDateEndLabelId()), - date = bet.endBetDate.formatToMediumDateNoYear(), - time = bet.endBetDate.formatToTime(), + label = stringResource(id = betDetail.bet.betStatus.getDateEndLabelId()), + date = betDetail.bet.endBetDate.formatToMediumDateNoYear(), + time = betDetail.bet.endBetDate.formatToTime(), modifier = Modifier.width(IntrinsicSize.Max) ) } Spacer(modifier = Modifier.height(20.dp)) } - if (bet.betStatus is BetStatus.Finished) { + if (betDetail.bet.betStatus is BetStatus.Finished) { BetStatusWinner( - answer = stringResource(id = R.string.Yes), + answer = response1Display, color = AllInTheme.colors.allInBlue, coinAmount = 442, username = "Imri", @@ -95,63 +116,150 @@ class BetStatusBottomSheetBetDisplayer( .padding(horizontal = 20.dp) ) { Spacer(modifier = Modifier.height(20.dp)) - YesNoStatBar(yesPercentage = .86f) + BinaryStatBar( + response1Percentage = remember { + val total = (response1Answer?.totalParticipants ?: 0) + (response2Answer?.totalParticipants ?: 0) + if (total == 0) .5f else (response1Answer?.totalParticipants ?: 0) / total.toFloat() + }, + response1 = response1Display, + response2 = response2Display + ) AllInDetailsDrawer { YesNoDetailsLine( icon = AllInTheme.icons.allCoins(), - yesText = "550", - noText = "330", + yesText = response1Answer?.totalStakes?.toString() ?: "0", + noText = response2Answer?.totalStakes?.toString() ?: "0" ) YesNoDetailsLine( icon = Icons.Filled.People, - yesText = "12", - noText = "5" + yesText = response1Answer?.totalParticipants?.toString() ?: "0", + noText = response2Answer?.totalParticipants?.toString() ?: "0" ) YesNoDetailsLine( icon = Icons.Filled.WorkspacePremium, - yesText = "45", - noText = "45" + yesText = response1Answer?.highestStake?.toString() ?: "0", + noText = response2Answer?.highestStake?.toString() ?: "0" ) YesNoDetailsLine( icon = Icons.Filled.EmojiEvents, - yesText = "x1.2", - noText = "x1.45" + yesText = "x${response1Answer?.odds?.formatToSimple(locale) ?: "1.00"}", + noText = "x${response2Answer?.odds?.formatToSimple(locale) ?: "1.00"}" ) } + + Text( + text = stringResource(id = R.string.bet_status_participants_list), + fontSize = 20.sp, + color = AllInTheme.themeColors.onMainSurface, + style = AllInTheme.typography.h1, + modifier = Modifier.padding(vertical = 36.dp) + ) + LazyColumn( + verticalArrangement = Arrangement.spacedBy(8.dp), + horizontalAlignment = Alignment.CenterHorizontally, + contentPadding = PaddingValues(horizontal = 13.dp, vertical = 8.dp), + modifier = Modifier.fillMaxHeight() + ) { + betDetail.userParticipation?.let { + item { + BetStatusParticipant( + username = it.username, + allCoinsAmount = it.stake + ) + HorizontalDivider( + color = AllInTheme.themeColors.border, + modifier = Modifier.padding(vertical = 8.dp, horizontal = 25.dp) + ) + } + } + items(betDetail.participations) { + if (it.username != betDetail.userParticipation?.username) { + BetStatusParticipant( + username = it.username, + allCoinsAmount = it.stake + ) + } + } + } } } - if (bet.betStatus !is BetStatus.Finished) { + if (betDetail.bet.betStatus !is BetStatus.Finished && betDetail.userParticipation == null) { RainbowButton( modifier = Modifier .align(Alignment.BottomCenter) .padding(horizontal = 7.dp), text = stringResource(id = R.string.Participate), - enabled = bet.betStatus == BetStatus.Waiting, + enabled = betDetail.bet.betStatus == BetStatus.Waiting, onClick = openParticipateSheet ) } } } + @OptIn(ExperimentalMaterial3Api::class) @Composable - override fun DisplayMatchBet(bet: MatchBet) { - Text("This is a MATCH BET") + override fun DisplayYesNoBet(betDetail: BetDetail) { + DisplayBinaryBet( + betDetail = betDetail, + response1 = YES_VALUE, + response2 = NO_VALUE, + response1Display = stringResource(id = R.string.Yes).uppercase(), + response2Display = stringResource(id = R.string.No).uppercase() + ) } @Composable - override fun DisplayCustomBet(bet: CustomBet) { + override fun DisplayMatchBet(betDetail: BetDetail) { + val bet = remember { betDetail.bet as MatchBet } + DisplayBinaryBet( + betDetail = betDetail, + response1 = bet.nameTeam1, + response2 = bet.nameTeam2 + ) + } + + @Composable + override fun DisplayCustomBet(betDetail: BetDetail) { Text("This is a CUSTOM BET") } } +@Composable +fun BetStatusParticipant( + username: String, + allCoinsAmount: Int +) { + Row( + modifier = Modifier.fillMaxWidth(), + horizontalArrangement = Arrangement.spacedBy(7.dp), + verticalAlignment = Alignment.CenterVertically + ) { + ProfilePicture(modifier = Modifier.size(25.dp)) + Text( + text = username, + fontWeight = FontWeight.Bold, + style = AllInTheme.typography.h2, + color = AllInTheme.themeColors.onMainSurface, + maxLines = 1, + overflow = TextOverflow.Ellipsis, + modifier = Modifier.weight(1f) + ) + AllInCoinCount( + amount = allCoinsAmount, + color = AllInTheme.colors.allInPurple + ) + } +} + @Preview @Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) @Composable private fun BetStatusBottomSheetPreview( - @PreviewParameter(BetWithStatusPreviewProvider::class) bet: Bet + @PreviewParameter(BetDetailPreviewProvider::class) bet: BetDetail ) { AllInTheme { - val coins = remember { mutableIntStateOf(100) } - BetStatusBottomSheetBetDisplayer {}.DisplayBet(bet) + BetStatusBottomSheetBetDisplayer { + + }.DisplayBet(bet) } } \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt index 7f57f2e..fdd9642 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainScreen.kt @@ -67,7 +67,7 @@ fun MainScreen( var loading by remember { mainViewModel.loading } val currentUser = remember { mainViewModel.currentUserState } - val (selectedBet, setSelectedBet) = remember { mainViewModel.selectedBet } + val selectedBet by remember { mainViewModel.selectedBet } val (wonBet, setWonBet) = remember { mainViewModel.wonBet } val (statusVisibility, sheetBackVisibility, setStatusVisibility) = rememberBetStatusVisibilities() val (participateSheetVisibility, setParticipateSheetVisibility) = remember { @@ -152,7 +152,7 @@ fun MainScreen( AllInDrawerNavHost( navController = navController, selectBet = { bet, participate -> - setSelectedBet(bet) + mainViewModel.openBetDetail(bet) setParticipateSheetVisibility(participate) setStatusVisibility(true) }, @@ -182,11 +182,11 @@ fun MainScreen( sheetVisibility = statusVisibility.value, sheetBackVisibility = sheetBackVisibility.value, onDismiss = { setStatusVisibility(false) }, - bet = selectedBet, + betDetail = selectedBet, paddingValues = betStatusDisplayer.paddingValues.value, displayBet = { betStatusDisplayer.DisplayBet(it) }, userCoinAmount = mainViewModel.currentUserState.userCoins, - onParticipate = { mainViewModel.participateToBet(it) }, + onParticipate = { stake, response -> mainViewModel.participateToBet(stake, response) }, participateSheetVisibility = participateSheetVisibility, setParticipateSheetVisibility = setParticipateSheetVisibility ) diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt index aac1fcf..a666bef 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/main/MainViewModel.kt @@ -8,16 +8,15 @@ import androidx.lifecycle.viewModelScope import dagger.hilt.android.lifecycle.HiltViewModel import fr.iut.alldev.allin.data.model.User import fr.iut.alldev.allin.data.model.bet.Bet -import fr.iut.alldev.allin.data.model.bet.BetFinishedStatus -import fr.iut.alldev.allin.data.model.bet.BetStatus -import fr.iut.alldev.allin.data.model.bet.YesNoBet +import fr.iut.alldev.allin.data.model.bet.Participation +import fr.iut.alldev.allin.data.model.bet.vo.BetDetail +import fr.iut.alldev.allin.data.repository.BetRepository import fr.iut.alldev.allin.di.AllInCurrentUser import fr.iut.alldev.allin.keystore.AllInKeystoreManager import fr.iut.alldev.allin.ui.core.snackbar.SnackbarType import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch import kotlinx.coroutines.withContext -import java.time.ZonedDateTime import javax.inject.Inject class UserState(val user: User) { @@ -27,23 +26,26 @@ class UserState(val user: User) { @HiltViewModel class MainViewModel @Inject constructor( @AllInCurrentUser val currentUser: User, + private val betRepository: BetRepository, private val keystoreManager: AllInKeystoreManager ) : ViewModel() { var loading = mutableStateOf(false) val currentUserState = UserState(currentUser) - val selectedBet = mutableStateOf(null) + val selectedBet = mutableStateOf(null) val wonBet = mutableStateOf( - YesNoBet( - theme = "Theme", - phrase = "Phrase", - endRegisterDate = ZonedDateTime.now(), - endBetDate = ZonedDateTime.now(), - isPublic = true, - betStatus = BetStatus.Finished(BetFinishedStatus.WON), - creator = "creator" - ) + null + /* YesNoBet( + id = "1", + theme = "Theme", + phrase = "Phrase", + endRegisterDate = ZonedDateTime.now(), + endBetDate = ZonedDateTime.now(), + isPublic = true, + betStatus = BetStatus.Finished(BetFinishedStatus.WON), + creator = "creator" + )*/ ) val snackbarContent: MutableState by lazy { mutableStateOf(null) } @@ -51,6 +53,11 @@ class MainViewModel @Inject constructor( snackbarContent.value = content } + fun openBetDetail(bet: Bet) { + viewModelScope.launch { + selectedBet.value = betRepository.getBet(bet.id, keystoreManager.getToken() ?: "") + } + } fun deleteToken() { viewModelScope.launch { @@ -58,12 +65,20 @@ class MainViewModel @Inject constructor( } } - fun participateToBet(stake: Int) { + fun participateToBet(stake: Int, response: String) { viewModelScope.launch { withContext(Dispatchers.IO) { loading.value = true currentUserState.userCoins.intValue -= stake - Thread.sleep(1000) + selectedBet.value?.bet?.let { + val participation = Participation( + betId = it.id, + username = currentUser.username, + response = response, + stake = stake + ) + betRepository.participateToBet(participation, keystoreManager.getToken() ?: "") + } loading.value = false } } diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetDetailPreviewProvider.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetDetailPreviewProvider.kt new file mode 100644 index 0000000..154f04c --- /dev/null +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetDetailPreviewProvider.kt @@ -0,0 +1,58 @@ +package fr.iut.alldev.allin.ui.preview + +import androidx.compose.ui.tooling.preview.PreviewParameterProvider +import fr.iut.alldev.allin.data.model.bet.NO_VALUE +import fr.iut.alldev.allin.data.model.bet.Participation +import fr.iut.alldev.allin.data.model.bet.YES_VALUE +import fr.iut.alldev.allin.data.model.bet.vo.BetAnswerDetail +import fr.iut.alldev.allin.data.model.bet.vo.BetDetail + +class BetDetailPreviewProvider : PreviewParameterProvider { + override val values = BetWithStatusPreviewProvider().values.map { + BetDetail( + bet = it, + answers = listOf( + BetAnswerDetail( + response = YES_VALUE, + totalStakes = 300, + totalParticipants = 2, + highestStake = 200, + odds = 1.0f + ), + BetAnswerDetail( + response = NO_VALUE, + totalStakes = 150, + totalParticipants = 1, + highestStake = 150, + odds = 2.0f + ), + ), + participations = listOf( + Participation( + betId = it.id, + username = "User1", + response = YES_VALUE, + stake = 200 + ), + Participation( + betId = it.id, + username = "User2", + response = YES_VALUE, + stake = 100 + ), + Participation( + betId = it.id, + username = "MyUser", + response = NO_VALUE, + stake = 150 + ) + ), + userParticipation = Participation( + betId = it.id, + username = "MyUser", + response = NO_VALUE, + stake = 150 + ) + ) + } +} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt index dabcded..3a97a59 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetPreviewProvider.kt @@ -12,6 +12,7 @@ import java.time.ZonedDateTime class BetPreviewProvider : PreviewParameterProvider { override val values = sequenceOf( YesNoBet( + id = "1", theme = "Theme", phrase = "Phrase", endRegisterDate = ZonedDateTime.now(), @@ -21,6 +22,7 @@ class BetPreviewProvider : PreviewParameterProvider { creator = "creator" ), MatchBet( + id = "2", theme = "Theme", phrase = "Phrase", endRegisterDate = ZonedDateTime.now(), @@ -32,6 +34,7 @@ class BetPreviewProvider : PreviewParameterProvider { nameTeam2 = "Climate Change" ), CustomBet( + id = "3", theme = "Theme", phrase = "Phrase", endRegisterDate = ZonedDateTime.now(), diff --git a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt index fcc5adb..e5b3721 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/ui/preview/BetWithStatusPreviewProvider.kt @@ -13,6 +13,7 @@ class BetWithStatusPreviewProvider : PreviewParameterProvider { override val values = BetStatus.entries.flatMap { status -> sequenceOf( YesNoBet( + id = "1", theme = "Theme", phrase = "Phrase", endRegisterDate = ZonedDateTime.now(), @@ -22,6 +23,7 @@ class BetWithStatusPreviewProvider : PreviewParameterProvider { creator = "creator" ), MatchBet( + id = "2", theme = "Theme", phrase = "Phrase", endRegisterDate = ZonedDateTime.now(), @@ -33,6 +35,7 @@ class BetWithStatusPreviewProvider : PreviewParameterProvider { nameTeam2 = "Climate Change" ), CustomBet( + id = "3", theme = "Theme", phrase = "Phrase", endRegisterDate = ZonedDateTime.now(), diff --git a/src/app/src/main/java/fr/iut/alldev/allin/utils/Tuples.kt b/src/app/src/main/java/fr/iut/alldev/allin/utils/Tuples.kt deleted file mode 100644 index 922ca6e..0000000 --- a/src/app/src/main/java/fr/iut/alldev/allin/utils/Tuples.kt +++ /dev/null @@ -1,12 +0,0 @@ -package fr.iut.alldev.allin.utils - -import java.io.Serializable - -data class Quadruple( - val first: A, - val second: B, - val third: C, - val fourth: D -) : Serializable { - override fun toString(): String = "($first, $second, $third, $fourth)" -} \ No newline at end of file diff --git a/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt b/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt index be89c05..40b2cb8 100644 --- a/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt +++ b/src/app/src/main/java/fr/iut/alldev/allin/vo/bet/BetDisplayer.kt @@ -1,27 +1,27 @@ package fr.iut.alldev.allin.vo.bet import androidx.compose.runtime.Composable -import fr.iut.alldev.allin.data.model.bet.Bet import fr.iut.alldev.allin.data.model.bet.CustomBet import fr.iut.alldev.allin.data.model.bet.MatchBet import fr.iut.alldev.allin.data.model.bet.YesNoBet +import fr.iut.alldev.allin.data.model.bet.vo.BetDetail interface BetDisplayer { @Composable - fun DisplayBet(bet: Bet){ - when(bet){ - is CustomBet -> DisplayCustomBet(bet) - is MatchBet -> DisplayMatchBet(bet) - is YesNoBet -> DisplayYesNoBet(bet) + fun DisplayBet(betDetail: BetDetail) { + when (betDetail.bet) { + is CustomBet -> DisplayCustomBet(betDetail) + is MatchBet -> DisplayMatchBet(betDetail) + is YesNoBet -> DisplayYesNoBet(betDetail) } } @Composable - fun DisplayYesNoBet(bet: YesNoBet) + fun DisplayYesNoBet(betDetail: BetDetail) @Composable - fun DisplayMatchBet(bet: MatchBet) + fun DisplayMatchBet(betDetail: BetDetail) @Composable - fun DisplayCustomBet(bet: CustomBet) + fun DisplayCustomBet(betDetail: BetDetail) } \ No newline at end of file diff --git a/src/app/src/main/res/values-fr/strings.xml b/src/app/src/main/res/values-fr/strings.xml index 0b953ca..0f1e299 100644 --- a/src/app/src/main/res/values-fr/strings.xml +++ b/src/app/src/main/res/values-fr/strings.xml @@ -118,6 +118,7 @@ En cours… En attente… Faites vos paris + Liste des participants En cours diff --git a/src/app/src/main/res/values/strings.xml b/src/app/src/main/res/values/strings.xml index f1c5ad9..328e981 100644 --- a/src/app/src/main/res/values/strings.xml +++ b/src/app/src/main/res/values/strings.xml @@ -118,6 +118,7 @@ In progress… Waiting… Place your bets + Participants Current diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/api/AllInApi.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/api/AllInApi.kt index 413113e..550c182 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/api/AllInApi.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/api/AllInApi.kt @@ -2,15 +2,22 @@ package fr.iut.alldev.allin.data.api import fr.iut.alldev.allin.data.api.model.CheckUser import fr.iut.alldev.allin.data.api.model.RequestBet +import fr.iut.alldev.allin.data.api.model.RequestParticipation import fr.iut.alldev.allin.data.api.model.RequestUser import fr.iut.alldev.allin.data.api.model.ResponseBet +import fr.iut.alldev.allin.data.api.model.ResponseBetDetail import fr.iut.alldev.allin.data.api.model.ResponseUser import retrofit2.http.Body import retrofit2.http.GET import retrofit2.http.Header import retrofit2.http.POST +import retrofit2.http.Path interface AllInApi { + companion object { + fun String.formatBearerToken() = "Bearer $this" + } + @POST("users/login") suspend fun login(@Body body: CheckUser): ResponseUser @@ -25,4 +32,10 @@ interface AllInApi { @GET("bets/gets") suspend fun getAllBets(): List + + @GET("betdetail/get/{id}") + suspend fun getBet(@Header("Authorization") token: String, @Path("id") id: String): ResponseBetDetail + + @POST("participations/add") + suspend fun participateToBet(@Header("Authorization") token: String, @Body body: RequestParticipation) } \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/api/MockAllInApi.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/api/MockAllInApi.kt index 4b61b9b..f2b7f72 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/api/MockAllInApi.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/api/MockAllInApi.kt @@ -3,8 +3,12 @@ package fr.iut.alldev.allin.data.api import fr.iut.alldev.allin.data.api.interceptors.AllInAPIException import fr.iut.alldev.allin.data.api.model.CheckUser import fr.iut.alldev.allin.data.api.model.RequestBet +import fr.iut.alldev.allin.data.api.model.RequestParticipation import fr.iut.alldev.allin.data.api.model.RequestUser import fr.iut.alldev.allin.data.api.model.ResponseBet +import fr.iut.alldev.allin.data.api.model.ResponseBetAnswerDetail +import fr.iut.alldev.allin.data.api.model.ResponseBetDetail +import fr.iut.alldev.allin.data.api.model.ResponseParticipation import fr.iut.alldev.allin.data.api.model.ResponseUser import fr.iut.alldev.allin.data.model.bet.NO_VALUE import fr.iut.alldev.allin.data.model.bet.YES_VALUE @@ -12,13 +16,30 @@ import java.time.ZonedDateTime import java.util.UUID class MockAllInApi : AllInApi { + + private fun getUserFromToken(token: String) = + mockUsers.find { it.first.token == token } + + private fun getAnswerDetails(bet: ResponseBet, participations: List): List { + return bet.response.map { response -> + val responseParticipations = participations.filter { it.answer == response } + ResponseBetAnswerDetail( + response = response, + totalStakes = responseParticipations.sumOf { it.stake }, + totalParticipants = responseParticipations.size, + highestStake = responseParticipations.maxOfOrNull { it.stake } ?: 0, + odds = if (participations.isEmpty()) 0.0f else responseParticipations.size / participations.size.toFloat() + ) + } + } + override suspend fun login(body: CheckUser): ResponseUser { - return users.find { it.first.username == body.login && it.second == body.password }?.first + return mockUsers.find { it.first.username == body.login && it.second == body.password }?.first ?: throw AllInAPIException("Invalid login/password.") } override suspend fun login(token: String): ResponseUser { - return users.find { it.first.token == token }?.first + return getUserFromToken(token)?.first ?: throw AllInAPIException("Invalid token") } @@ -27,10 +48,10 @@ class MockAllInApi : AllInApi { id = UUID.randomUUID().toString(), username = body.username, email = body.email, - nbCoins = body.nbCoins, - token = "${body.username} ${users.size}" + nbCoins = 500, + token = "${body.username} ${mockUsers.size}" ) to body.password - users.add(response) + mockUsers.add(response) return response.first } @@ -50,16 +71,138 @@ class MockAllInApi : AllInApi { } override suspend fun getAllBets(): List = mockBets.toList() + override suspend fun getBet(token: String, id: String): ResponseBetDetail { + val bet = mockBets.find { it.id == id } ?: throw AllInAPIException("Bet not found") + val user = getUserFromToken(token) ?: throw AllInAPIException("Invalid login/password.") + val betParticipations = mockParticipations.filter { it.betId == bet.id } + val userParticipation = betParticipations.find { it.username == user.first.username } + + return ResponseBetDetail( + bet = bet, + answers = getAnswerDetails(bet, betParticipations), + participations = betParticipations, + userParticipation = userParticipation + ) + } + + override suspend fun participateToBet(token: String, body: RequestParticipation) { + getUserFromToken(token)?.let { + mockParticipations.add( + ResponseParticipation( + id = "", + betId = body.betId, + username = it.first.username, + answer = body.answer, + stake = body.stake + + ) + ) + } ?: throw AllInAPIException("Invalid token") + } } -private val users = mutableListOf( +private val mockUsers = mutableListOf( ResponseUser( id = "UUID 1", username = "User 1", email = "john@doe.fr", nbCoins = 250, token = "token 1" - ) to "psswrd" + ) to "12345", + ResponseUser( + id = "UUID 2", + username = "User 2", + email = "john@doe.fr", + nbCoins = 250, + token = "token 2" + ) to "12345", + ResponseUser( + id = "UUID 3", + username = "User 3", + email = "john@doe.fr", + nbCoins = 250, + token = "token 3" + ) to "12345", + ResponseUser( + id = "UUID 4", + username = "User 4", + email = "john@doe.fr", + nbCoins = 250, + token = "token 4" + ) to "12345", + ResponseUser( + id = "UUID 5", + username = "User 5", + email = "john@doe.fr", + nbCoins = 250, + token = "token 5" + ) to "12345", + ResponseUser( + id = "UUID 6", + username = "User 6", + email = "john@doe.fr", + nbCoins = 250, + token = "token 6" + ) to "12345", + ResponseUser( + id = "UUID 7", + username = "User 7", + email = "john@doe.fr", + nbCoins = 250, + token = "token 7" + ) to "12345" +) + +private val mockParticipations = mutableListOf( + ResponseParticipation( + id = "", + betId = "UUID1", + username = mockUsers[0].first.username, + answer = YES_VALUE, + stake = 200 + ), + ResponseParticipation( + id = "", + betId = "UUID1", + username = mockUsers[1].first.username, + answer = NO_VALUE, + stake = 1500 + ), + ResponseParticipation( + id = "", + betId = "UUID1", + username = mockUsers[2].first.username, + answer = YES_VALUE, + stake = 300 + ), + ResponseParticipation( + id = "", + betId = "UUID1", + username = mockUsers[3].first.username, + answer = YES_VALUE, + stake = 25 + ), + ResponseParticipation( + id = "", + betId = "UUID1", + username = mockUsers[4].first.username, + answer = NO_VALUE, + stake = 222 + ), + ResponseParticipation( + id = "", + betId = "UUID1", + username = mockUsers[5].first.username, + answer = NO_VALUE, + stake = 222 + ), + ResponseParticipation( + id = "", + betId = "UUID1", + username = mockUsers[6].first.username, + answer = NO_VALUE, + stake = 222 + ) ) private val mockBets = mutableListOf( diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/api/interceptors/ErrorInterceptor.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/api/interceptors/ErrorInterceptor.kt index 16abb5a..ebbd8a7 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/api/interceptors/ErrorInterceptor.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/api/interceptors/ErrorInterceptor.kt @@ -14,14 +14,15 @@ class ErrorInterceptor : Interceptor { override fun intercept(chain: Interceptor.Chain): Response { val request = chain.request() val response = chain.proceed(request) - if(!response.isSuccessful){ + if (!response.isSuccessful) { when (response.code) { 404 -> throw AllInNotFoundException(response.message) 401 -> throw AllInUnauthorizedException(response.message) else -> throw AllInUnsuccessfulException(response.message) } } - if (response.body?.contentType()?.subtype != "json") { + + response.body?.contentType()?.subtype?.takeIf { it != "json" }?.let { throw AllInAPIException(response.message) } diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt index 4eca5f1..3610752 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiBet.kt @@ -7,7 +7,9 @@ import fr.iut.alldev.allin.data.model.bet.CustomBet import fr.iut.alldev.allin.data.model.bet.NO_VALUE import fr.iut.alldev.allin.data.model.bet.YES_VALUE import fr.iut.alldev.allin.data.model.bet.YesNoBet -import fr.iut.alldev.allin.data.serialization.SimpleDateSerializer +import fr.iut.alldev.allin.data.model.bet.vo.BetAnswerDetail +import fr.iut.alldev.allin.data.model.bet.vo.BetDetail +import fr.iut.alldev.allin.data.serialization.ZonedDateTimeSerializer import kotlinx.serialization.Serializable import java.time.ZonedDateTime @@ -17,8 +19,8 @@ data class ResponseBet( val id: String?, val theme: String, val sentenceBet: String, - @Serializable(SimpleDateSerializer::class) val endRegistration: ZonedDateTime, - @Serializable(SimpleDateSerializer::class) var endBet: ZonedDateTime, + @Serializable(ZonedDateTimeSerializer::class) val endRegistration: ZonedDateTime, + @Serializable(ZonedDateTimeSerializer::class) var endBet: ZonedDateTime, var isPrivate: Boolean, var response: List, val createdBy: String @@ -26,6 +28,7 @@ data class ResponseBet( fun toBet(): Bet { if (response.toSet() == setOf(YES_VALUE, NO_VALUE)) { return YesNoBet( + id = id ?: "", theme = theme, phrase = sentenceBet, endRegisterDate = endRegistration, @@ -36,6 +39,7 @@ data class ResponseBet( ) } else { return CustomBet( + id = id ?: "", theme = theme, phrase = sentenceBet, endRegisterDate = endRegistration, @@ -52,10 +56,48 @@ data class ResponseBet( @Keep @Serializable data class RequestBet( + val id: String = "", val theme: String, val sentenceBet: String, - @Serializable(SimpleDateSerializer::class) val endRegistration: ZonedDateTime, - @Serializable(SimpleDateSerializer::class) var endBet: ZonedDateTime, + @Serializable(ZonedDateTimeSerializer::class) val endRegistration: ZonedDateTime, + @Serializable(ZonedDateTimeSerializer::class) var endBet: ZonedDateTime, var isPrivate: Boolean, var response: List ) + +@Keep +@Serializable +data class ResponseBetAnswerDetail( + val response: String, + val totalStakes: Int, + val totalParticipants: Int, + val highestStake: Int, + val odds: Float +) { + fun toAnswerDetail() = + BetAnswerDetail( + response = response, + totalStakes = totalStakes, + totalParticipants = totalParticipants, + highestStake = highestStake, + odds = odds + ) +} + +@Keep +@Serializable +data class ResponseBetDetail( + val bet: ResponseBet, + val answers: List, + val participations: List, + val userParticipation: ResponseParticipation? = null +) { + fun toBetDetail() = + BetDetail( + bet = bet.toBet(), + answers = answers.map { it.toAnswerDetail() }, + participations = participations.map { it.toParticipation() }, + userParticipation = userParticipation?.toParticipation() + + ) +} \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiParticipation.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiParticipation.kt new file mode 100644 index 0000000..488ca34 --- /dev/null +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiParticipation.kt @@ -0,0 +1,31 @@ +package fr.iut.alldev.allin.data.api.model + +import androidx.annotation.Keep +import fr.iut.alldev.allin.data.model.bet.Participation +import kotlinx.serialization.Serializable + +@Keep +@Serializable +data class ResponseParticipation( + val id: String, + val betId: String, + val username: String, + val answer: String, + val stake: Int +) { + fun toParticipation() = + Participation( + betId = betId, + username = username, + response = answer, + stake = stake + ) +} + +@Keep +@Serializable +data class RequestParticipation( + val betId: String, + val answer: String, + val stake: Int +) \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiUser.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiUser.kt index 79d1681..f6e021c 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiUser.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/api/model/ApiUser.kt @@ -9,24 +9,23 @@ import kotlinx.serialization.Serializable data class RequestUser( val username: String, val email: String, - val password: String, - var nbCoins: Int, + val password: String ) @Keep @Serializable data class ResponseUser( - val id: String, + val id: String = "", val username: String, val email: String, var nbCoins: Int, - var token: String? = null, + var token: String? = null ) { fun toUser() = User( id = id, username = username, email = email, - coins = nbCoins + coins = nbCoins.toInt() ) } diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/di/ApiModule.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/di/ApiModule.kt index 50c387a..9072cd8 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/di/ApiModule.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/di/ApiModule.kt @@ -11,7 +11,7 @@ import okhttp3.HttpUrl import okhttp3.OkHttpClient import javax.inject.Singleton -const val mock = true +const val mock = false @Module @InstallIn(SingletonComponent::class) diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/di/NetworkModule.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/di/NetworkModule.kt index 0c26aae..981005a 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/di/NetworkModule.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/di/NetworkModule.kt @@ -17,7 +17,7 @@ import javax.inject.Qualifier internal val json by lazy { Json { ignoreUnknownKeys = true - encodeDefaults = false + encodeDefaults = true } } diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/User.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/User.kt index 5a4e882..21d650b 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/User.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/User.kt @@ -1,8 +1,8 @@ package fr.iut.alldev.allin.data.model data class User( - val id : String, - val username : String, - val email : String, - val coins : Int + val id: String, + val username: String, + val email: String, + val coins: Int ) \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt index cc1910a..1f9cc17 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Bet.kt @@ -4,7 +4,7 @@ import fr.iut.alldev.allin.data.api.model.RequestBet import java.time.ZonedDateTime sealed class Bet( - open val id: String? = null, + open val id: String, open val creator: String, open val theme: String, open val phrase: String, @@ -16,6 +16,7 @@ sealed class Bet( abstract fun getResponses(): List fun toRequestBet(): RequestBet { return RequestBet( + id = "", theme = theme, sentenceBet = phrase, endRegistration = endRegisterDate, diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetFactory.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetFactory.kt index c194a30..8df4afb 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetFactory.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/BetFactory.kt @@ -5,6 +5,7 @@ import java.time.ZonedDateTime class BetFactory { companion object { fun createBet( + id: String, betType: BetType, creator: String, theme: String, @@ -20,6 +21,7 @@ class BetFactory { when (betType) { BetType.YES_NO -> { YesNoBet( + id = id, theme = theme, creator = creator, phrase = phrase, @@ -32,6 +34,7 @@ class BetFactory { BetType.MATCH -> { MatchBet( + id = id, theme = theme, creator = creator, phrase = phrase, @@ -47,6 +50,7 @@ class BetFactory { BetType.CUSTOM -> { CustomBet( + id = id, theme = theme, creator = creator, phrase = phrase, diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/CustomBet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/CustomBet.kt index 8af1e5e..a252e51 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/CustomBet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/CustomBet.kt @@ -3,7 +3,7 @@ package fr.iut.alldev.allin.data.model.bet import java.time.ZonedDateTime data class CustomBet( - override val id: String? = null, + override val id: String, override val creator: String, override val theme: String, override val phrase: String, diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/MatchBet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/MatchBet.kt index 4e96674..03a829e 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/MatchBet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/MatchBet.kt @@ -3,7 +3,7 @@ package fr.iut.alldev.allin.data.model.bet import java.time.ZonedDateTime data class MatchBet( - override val id: String? = null, + override val id: String, override val creator: String, override val theme: String, override val phrase: String, diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Participation.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Participation.kt new file mode 100644 index 0000000..e2f15b1 --- /dev/null +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/Participation.kt @@ -0,0 +1,17 @@ +package fr.iut.alldev.allin.data.model.bet + +import fr.iut.alldev.allin.data.api.model.RequestParticipation + +data class Participation( + val betId: String, + val username: String, + val response: String, + val stake: Int +) { + fun toRequestParticipation() = + RequestParticipation( + betId = betId, + answer = response, + stake = stake + ) +} \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/YesNoBet.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/YesNoBet.kt index 2c57d4e..5e28f06 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/YesNoBet.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/YesNoBet.kt @@ -6,7 +6,7 @@ const val YES_VALUE = "Yes" const val NO_VALUE = "No" data class YesNoBet( - override val id: String? = null, + override val id: String, override val creator: String, override val theme: String, override val phrase: String, diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetAnswerDetail.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetAnswerDetail.kt new file mode 100644 index 0000000..382a4b3 --- /dev/null +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetAnswerDetail.kt @@ -0,0 +1,9 @@ +package fr.iut.alldev.allin.data.model.bet.vo + +data class BetAnswerDetail( + val response: String, + val totalStakes: Int, + val totalParticipants: Int, + val highestStake: Int, + val odds: Float +) \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetDetail.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetDetail.kt new file mode 100644 index 0000000..a77f6dd --- /dev/null +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetDetail.kt @@ -0,0 +1,14 @@ +package fr.iut.alldev.allin.data.model.bet.vo + +import fr.iut.alldev.allin.data.model.bet.Bet +import fr.iut.alldev.allin.data.model.bet.Participation + +data class BetDetail( + val bet: Bet, + val answers: List, + val participations: List, + val userParticipation: Participation? +) { + fun getAnswerOfResponse(response: String) = + answers.find { it.response == response } +} \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetResult.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetResult.kt new file mode 100644 index 0000000..407bc4e --- /dev/null +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/model/bet/vo/BetResult.kt @@ -0,0 +1,10 @@ +package fr.iut.alldev.allin.data.model.bet.vo + +import fr.iut.alldev.allin.data.model.bet.Bet +import fr.iut.alldev.allin.data.model.bet.Participation + +data class BetResult( + val bet: Bet, + val participations: List, + val answerDetail: BetAnswerDetail +) \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/repository/BetRepository.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/repository/BetRepository.kt index bec1d9c..ed4bcd8 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/repository/BetRepository.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/repository/BetRepository.kt @@ -1,11 +1,15 @@ package fr.iut.alldev.allin.data.repository import fr.iut.alldev.allin.data.model.bet.Bet +import fr.iut.alldev.allin.data.model.bet.Participation +import fr.iut.alldev.allin.data.model.bet.vo.BetDetail import kotlinx.coroutines.flow.Flow abstract class BetRepository { abstract suspend fun createBet(bet: Bet, token: String) abstract suspend fun getHistory(): Flow> abstract suspend fun getCurrentBets(): Flow> + abstract suspend fun getBet(id: String, token: String): BetDetail + abstract suspend fun participateToBet(participation: Participation, token: String) abstract suspend fun getAllBets(): Flow> } \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/repository/UserRepository.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/repository/UserRepository.kt index 338b8aa..b9a22ac 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/repository/UserRepository.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/repository/UserRepository.kt @@ -4,16 +4,9 @@ import fr.iut.alldev.allin.data.model.User abstract class UserRepository { lateinit var currentUser: User - abstract suspend fun login( - username: String, - password: String - ): String? + abstract suspend fun login(username: String, password: String): String? abstract suspend fun login(token: String): String? - abstract suspend fun register( - username: String, - email: String, - password: String - ): String? + abstract suspend fun register(username: String, email: String, password: String): String? } \ No newline at end of file diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/BetRepositoryImpl.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/BetRepositoryImpl.kt index 1c21c87..7748092 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/BetRepositoryImpl.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/BetRepositoryImpl.kt @@ -1,10 +1,13 @@ package fr.iut.alldev.allin.data.repository.impl import fr.iut.alldev.allin.data.api.AllInApi +import fr.iut.alldev.allin.data.api.AllInApi.Companion.formatBearerToken import fr.iut.alldev.allin.data.model.bet.Bet import fr.iut.alldev.allin.data.model.bet.BetFinishedStatus import fr.iut.alldev.allin.data.model.bet.BetStatus +import fr.iut.alldev.allin.data.model.bet.Participation import fr.iut.alldev.allin.data.model.bet.YesNoBet +import fr.iut.alldev.allin.data.model.bet.vo.BetDetail import fr.iut.alldev.allin.data.repository.BetRepository import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.flowOf @@ -16,7 +19,7 @@ class BetRepositoryImpl @Inject constructor( ) : BetRepository() { override suspend fun createBet(bet: Bet, token: String) { api.createBet( - token = token, + token = token.formatBearerToken(), body = bet.toRequestBet() ) } @@ -25,6 +28,7 @@ class BetRepositoryImpl @Inject constructor( return flowOf( listOf( YesNoBet( + id = "1", creator = "Lucas", theme = "Theme", phrase = "Bet phrase 1", @@ -34,6 +38,7 @@ class BetRepositoryImpl @Inject constructor( betStatus = BetStatus.Finished(BetFinishedStatus.WON) ), YesNoBet( + id = "2", creator = "Lucas", theme = "Theme", phrase = "Bet phrase 2", @@ -43,6 +48,7 @@ class BetRepositoryImpl @Inject constructor( betStatus = BetStatus.Finished(BetFinishedStatus.LOST) ), YesNoBet( + id = "3", creator = "Lucas", theme = "Theme", phrase = "Bet phrase 3", @@ -60,6 +66,7 @@ class BetRepositoryImpl @Inject constructor( return flowOf( listOf( YesNoBet( + id = "1", creator = "Lucas", theme = "Theme", phrase = "Bet phrase 1", @@ -69,6 +76,7 @@ class BetRepositoryImpl @Inject constructor( betStatus = BetStatus.InProgress ), YesNoBet( + id = "2", creator = "Lucas", theme = "Theme", phrase = "Bet phrase 2", @@ -78,6 +86,7 @@ class BetRepositoryImpl @Inject constructor( betStatus = BetStatus.InProgress ), YesNoBet( + id = "3", creator = "Lucas", theme = "Theme", phrase = "Bet phrase 3", @@ -90,6 +99,17 @@ class BetRepositoryImpl @Inject constructor( ) } + override suspend fun getBet(id: String, token: String): BetDetail { + return api.getBet( + token = token.formatBearerToken(), + id = id + ).toBetDetail() + } + + override suspend fun participateToBet(participation: Participation, token: String) { + api.participateToBet(token = token.formatBearerToken(), body = participation.toRequestParticipation()) + } + override suspend fun getAllBets(): Flow> { return flowOf( api.getAllBets().map { it.toBet() } diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/UserRepositoryImpl.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/UserRepositoryImpl.kt index 54f3889..6c23cd8 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/UserRepositoryImpl.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/repository/impl/UserRepositoryImpl.kt @@ -1,6 +1,7 @@ package fr.iut.alldev.allin.data.repository.impl import fr.iut.alldev.allin.data.api.AllInApi +import fr.iut.alldev.allin.data.api.AllInApi.Companion.formatBearerToken import fr.iut.alldev.allin.data.api.model.CheckUser import fr.iut.alldev.allin.data.api.model.RequestUser import fr.iut.alldev.allin.data.repository.UserRepository @@ -22,7 +23,7 @@ class UserRepositoryImpl @Inject constructor( } override suspend fun login(token: String): String? { - val response = api.login(token = "Bearer $token") + val response = api.login(token = token.formatBearerToken()) currentUser = response.toUser() return response.token } @@ -33,8 +34,7 @@ class UserRepositoryImpl @Inject constructor( RequestUser( username = username, email = email, - password = password, - nbCoins = 0 + password = password ) ) currentUser = response.toUser() diff --git a/src/data/src/main/java/fr/iut/alldev/allin/data/serialization/ZonedDateTimeSerializer.kt b/src/data/src/main/java/fr/iut/alldev/allin/data/serialization/ZonedDateTimeSerializer.kt index 5810189..ae4742b 100644 --- a/src/data/src/main/java/fr/iut/alldev/allin/data/serialization/ZonedDateTimeSerializer.kt +++ b/src/data/src/main/java/fr/iut/alldev/allin/data/serialization/ZonedDateTimeSerializer.kt @@ -6,39 +6,22 @@ import kotlinx.serialization.descriptors.PrimitiveSerialDescriptor import kotlinx.serialization.descriptors.SerialDescriptor import kotlinx.serialization.encoding.Decoder import kotlinx.serialization.encoding.Encoder -import java.time.Instant -import java.time.LocalDate -import java.time.ZoneId import java.time.ZonedDateTime import java.time.format.DateTimeFormatter object ZonedDateTimeSerializer : KSerializer { + private val formatter: DateTimeFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss Z") + override val descriptor: SerialDescriptor = - PrimitiveSerialDescriptor("ZonedDateTime", PrimitiveKind.LONG) + PrimitiveSerialDescriptor("ZonedDateTime", PrimitiveKind.STRING) override fun serialize(encoder: Encoder, value: ZonedDateTime) { - encoder.encodeLong(value.toEpochSecond()) + encoder.encodeString(formatter.format(value)) } override fun deserialize(decoder: Decoder): ZonedDateTime { - val epoch = decoder.decodeLong() - return ZonedDateTime.ofInstant(Instant.ofEpochSecond(epoch), ZoneId.systemDefault()) + val dateString = decoder.decodeString() + return ZonedDateTime.parse(dateString, formatter) } } -class SimpleDateSerializer : KSerializer { - override val descriptor: SerialDescriptor = - PrimitiveSerialDescriptor("Date", PrimitiveKind.STRING) - - private val formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss") - - override fun deserialize(decoder: Decoder): ZonedDateTime { - val date = LocalDate.parse(decoder.decodeString(), formatter) - return date.atStartOfDay(ZoneId.systemDefault()) - } - - override fun serialize(encoder: Encoder, value: ZonedDateTime) { - val dateString = formatter.format(value) - encoder.encodeString(dateString) - } -}

;-n5oyX`D$eZ$Z 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 diff --git a/src/app/src/main/res/font/plusjakartasans_medium.ttf b/src/app/src/main/res/font/plusjakartasans_medium.ttf deleted file mode 100644 index 1e58066f4a1de5084ce84fafadf1ed85c73d82de..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 94816 zcmeFa2Yi&p+BQDr$);>bZ$Jo}N)OrHG&-pyw9tDCNg#nVQlyBA1w=(u)`}+U>-|p|4xo75nrr*<^nRy5$g!n-* z2md>6M zIN+33V6#lK;YMK!rqr0X#N#{Rn z+Hm1mL@L{A+6%QLMAK&QduduwgbX1Sq>SW~a*|7GpqG*oQb4lEESRcb zPKSFbB+;o4B}L#bX)yN(J(U!LyYZPuyOH2_x(nNK@J@%XRY-pt{H=j|6>Re*RZaSn zT9|7|^>4b1m=?gN%HQA^1YgDTec`7HNu+8hP!8Jx2(J)N*CGv0PD>MBO9Qt^RSiO_ zCS6Hq{Hqail?=NEbUaXk(BhFpRY+H7l1H+Uf?>#w61Z7lsz9hUpoW5)0%|7WQH3~I zG>6LVA{jRkGYeu?4qfDm1^mU5cPPrHKg@ZEi{N$jS>$Sgw5^8P5pE-(SIM}E&@IG@ z7z$WiVs>%3&e-IWD-b`CrhGCPs)*-Im_$eL0qpA+dH0-j=EHta3%qYB(*poT$rjk(BCk@q%8q(J=d`qcDk zX9_M~hdW(Vi<_3V4Phma6qI;3mXSU(-4~iq*t^o zwa|;}~%DRyoM{qnhi@eq1Y403=V(W*+_@Th`* zjLbuSJDD^?yU>MPO&+H?^lEw=T|!sU4fGBA89jwQv=g(l6gHZ@%0A=<_vXGlfVbo^ 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%0DR@~ml^ni~J8i!^+v9yh+M;kyjY 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