diff --git a/.firebase/hosting.YnVpbGQvd2Vi.cache b/.firebase/hosting.YnVpbGQvd2Vi.cache index f4d83c9f..8f1c2cb5 100644 --- a/.firebase/hosting.YnVpbGQvd2Vi.cache +++ b/.firebase/hosting.YnVpbGQvd2Vi.cache @@ -1,49 +1,78 @@ sqlite3.wasm,1741271571761,8e9753999ba85942d1a9a6c04be82ee46302f3a1f0aeba058a7bebae30841625 -manifest.json,1742052616326,d140e9b4ee89585110795b5694c8810100fa767bcaae0ccd87eff4c913d13ad5 -main.dart.js,1742190209674,a3b8a795e9b34e847e39638e72a5560f5fa0c01c45de09238d9d02cf7de4e2a1 -functions.js,1742052626416,c1c285b00096d7fef7dd8c06d7613cb917b93a3038a83f9be2783cc251fdd25f -flutter.js,1738903988000,8d47a0ef2a70705bf7e18df9c5148574acdff9bc412554b0784f1f46ba5918a4 -firebase-messaging-sw.js,1742052626416,eedb577a90ce796089ee56fbe936247b155b7de5f3ba19d4717b71b4bad8c426 +manifest.json,1752490781207,a757159d5701bd44c02424059e28c99edfd7fd9f176033bca5241c5d22032a6d +main.dart.js,1752490908489,65489c1b2e9f2acf767affd71d44842340037ac34d6abfbb5b05225d5e46e8fa +functions.js,1750668902266,9d3411e395dd7b9aa7362e74a6d9a89e16afc0bd71d8dcfc0ca9e256b0ba07de +flutter.js,1751939930000,053adb95c9fd7e93f05fde87a56d68d3269388c2678826834ffd3ed7d292bf26 +firebase-messaging-sw.js,1751874063698,7f16d7008b5751ac8a85c1135b85c0d1f65bd9122d79bc50ad318b3e507eca4c +favicon.ico,1750668902266,f9a33e18c8eda1a025b8bc80736ac4cb93ff348dc42f1dd19d34eb30080e4c73 drift_worker.dart.js,1741271571758,06ac27c648f4e1b3d5f75980fd2ffd502e43ab8a36baafa6a85f2fd0f95b1367 -icons/android-chrome-512x512.png,1742163336000,ecea49f2fa9a08b5245e9f8e6d0a45fd5388508fc280fad141e53d1e9acefff4 +icons/android-chrome-512x512.png,1750668902267,ecea49f2fa9a08b5245e9f8e6d0a45fd5388508fc280fad141e53d1e9acefff4 +icons/android-chrome-192x192.png,1750668902266,6d7ee72aa1c5ac35e5dd1ab12f907f6d8cecce25ff518884cea0a275fb090167 icons/Icon-maskable-512.png,1738903832255,e7983524dc70254adc61764657d7e03d19284de8da586b5818d737bc08c6d14e icons/Icon-maskable-192.png,1738903832254,dd96c123fdf6817cdf7e63d9693bcc246bac2e3782a41a6952fa41c0617c5573 icons/Icon-512.png,1738903832254,7a31ce91e554f1941158ca46f31c7f3f2b7c8c129229ea74a8fae1affe335033 -icons/Icon-192.png,1742163336000,6d7ee72aa1c5ac35e5dd1ab12f907f6d8cecce25ff518884cea0a275fb090167 -canvaskit/skwasm_st.wasm,1738904552000,669c860c596b623d7c98a6b4c60d2bcadc92d13ee78b7e565612eb7d2b96b04c -canvaskit/skwasm_st.js.symbols,1738904552000,dbf1ecd2987907700e49fee8eef71967eaf756e205fb2e97cd9c4b239ab4c2e2 -canvaskit/skwasm_st.js,1738904552000,5099d82713c753802530620e167e0f11fb72010175acb07527e54e55b725612d -canvaskit/skwasm.wasm,1738904476000,c9ad2544aaa0ce1958582d30599bef88b49be0df5c0c2b83c096b07232bca473 -canvaskit/skwasm.js.symbols,1738904476000,c063e47b2ede178417c06d899f69de3545140120712c2bca349b35209b1aeec5 -canvaskit/skwasm.js,1738904476000,378f5e2d7b590c1c638f783163e05c8df438118d9b9908f673bf15669fb014a5 -canvaskit/canvaskit.wasm,1738904372000,f8d74a0d0fa6b9d9bd9a040b6fff8425d629e9b28e840da9a8ab87ababcac878 -canvaskit/canvaskit.js.symbols,1738904372000,6262f5b2f99aabf760dbb4c592e02365ad32acb14252cb23ad9cbe42b39b5ae6 -canvaskit/canvaskit.js,1738904372000,b6506e44bdf978464c0d0c09ce64a9963df9477ae5198b38df82b83f380bfd25 -canvaskit/chromium/canvaskit.wasm,1738904398000,cfcbb6f12d5f5846a8a53873c929949b31eac8013d73fa34eaba28a7b6679a56 -canvaskit/chromium/canvaskit.js.symbols,1738904398000,02c8ca3407599c63e420fc8b9a5e5b5864fa29af85d7a33915273d7ec0d446bd -canvaskit/chromium/canvaskit.js,1738904398000,4321eb032e18194de43ed6955c201db6bec385f36c5d282da35dc62950d01e8f -assets/packages/assets/pubspec.yaml,1740755364270,97f7c5dd9c68dd4d7f2f8f9d70164b968cef244070ee02a85f5b217ca53b41ce +icons/Icon-192.png,1742367193073,6d7ee72aa1c5ac35e5dd1ab12f907f6d8cecce25ff518884cea0a275fb090167 +canvaskit/skwasm.wasm,1751940262000,bfcbd4b6e44b3118380e714f97dbab1b685b95bcd4a9c007bfa79c43b60c4b4d +canvaskit/skwasm.js.symbols,1751940262000,3bef5f28baf386a699e4b98893c94c0dd42ad82f1f93c1cdea532a75210aca11 +canvaskit/skwasm.js,1751940264000,28b1c6f000b61bd2f141dbc2d6dd2d4e8d78295593baea48ad52a9f8b0eca76b +canvaskit/canvaskit.wasm,1751940100000,c6fe626af107c4e97739d6c3062cfcb1f8e2eb75d8f1f657fdf77ac78b4dd934 +canvaskit/canvaskit.js.symbols,1751940100000,c58c818ceea58799cc5cfd951fa78f7607db6756342bd7a1aaeb1e431063894a +canvaskit/canvaskit.js,1751940100000,9b87a0d6c67ac68cbce3c8018ecc18f7d77811460b772cd0c51bba45d120136c +canvaskit/chromium/canvaskit.wasm,1751940174000,3b6125ac9e23794cf7f39985a7f21d8270fbdf5af7b30d1fa67a2b70061a1513 +canvaskit/chromium/canvaskit.js.symbols,1751940174000,6e864727463607c5ed93d9197e943eee281b93d814115f14e114defd31359f65 +canvaskit/chromium/canvaskit.js,1751940174000,98eed9e4311de4bc5e460d73ab0e034be11a0c0aded58733e94bf9971c8d1ecb +assets/packages/widgetbook/assets/logo.png,1741256900199,da3c6819025b53cf2a3bc0eff512193269452c0213a292a3a0dffc31bbe22bd7 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-ThinItalic.ttf,1741256900190,d3cc26ce5d1acad07fcd1a5810175ef93f05037fd501f70d92958f0e07d0c0b4 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-Thin.ttf,1741256900194,e53363da55b8bc62157e3aa4def2cf68e9968b78712f848dd2798154e438d9c3 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-SemiBoldItalic.ttf,1741256900195,6752603a5b29c70341ad377199d483cf73f5da20f1efe73526d25a0c1985232e +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-SemiBold.ttf,1741256900185,9ff2d627cf726339d98799c8593117646254a33a4384092eac7df61912e02d12 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-Regular.ttf,1741256900178,f615176f3a3b7edf54daa48faef435de8b016238911dc6824d31e93442799dd5 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-MediumItalic.ttf,1741256900177,b2a28a314091fd9e3e962d7cb59e54f9479623c60cd055a0a225d83e19ce71d2 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-Medium.ttf,1741256900182,317336af08dd76b61c0408fd9acb437d1fc0980c93b254e5cd6a5cd333b50a1b +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-LightItalic.ttf,1741256900193,bd7dbc534b976b66917f3a613d945181c3d889872e1a8f00bd860e54481ccab6 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-Light.ttf,1741256900189,0489dfd0e53f494827c309ab4cfc4b9de4ac441bb2816f19f2889850924e4963 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-Italic.ttf,1741256900198,93b9b71d19dd58bc9fe7f008778b4573248eddfb8dd550d5b55201e85997be80 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-ExtraLightItalic.ttf,1741256900174,b4dbe9ae34525bc4a2fd45fe951101261f1ebd11469d19c69496c78fe7f31360 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-ExtraLight.ttf,1741256900187,ccea34684b8b652c1471f6c6e5ce0170a3875c3433df790188d2d72121123d0d +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-ExtraBoldItalic.ttf,1741256900173,65be628568c2509c234d128daf299456b3e7de432498a50969d5456555051410 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-ExtraBold.ttf,1741256900183,f487ec93d1694fd0b33ccdbd97205c64089031db444ef1ec4a804f07ee77b749 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-BoldItalic.ttf,1741256900184,2b629c288425dcadc1b6f3dd6f6d336b3896cd74bc2846a7220efe46b3599452 +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-Bold.ttf,1741256900192,2b25219c282dc2b511dc717e6d2cc2dbd602a15786b7acf159701f17f169709d +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-BlackItalic.ttf,1741256900180,adf4afa9d526d683eae20cf3f4dc7d41b294d3c880b491c8a306527e01a76cff +assets/packages/widgetbook/assets/fonts/Poppins/Poppins-Black.ttf,1741256900197,7e6988176defbd8f12b2d2f419d57a37492413e17efaa36da9d3e92613563895 +assets/packages/assets/trash_can.svg,1751873154521,bfc4219e19a26cd0e89d0d1f46a0426bdddd20652ee3c8c9dc0d1d284b1c8a15 +assets/packages/assets/pubspec.yaml,1750668902247,dc38080715b81cfac02ffca13bf517064b171b31965a221d5324c70b9a6c3cc2 +assets/packages/assets/pubspec.lock,1750668902247,b180867dcd6eb5e27b92f5131f5f6ab630a047328ce3cfebcb169e9553762e5b assets/packages/assets/meatballs.svg,1740755364270,32314300150c2bbf11964bb161c1b56376cc720a347d0a282fe95bbb1ad6ea1a +assets/packages/assets/map_pin_fill.svg,1751873154521,82636f6ff1bec87b1c6d21cc3057fb17782dc3816cdcd633dcb2ba1b0aa0e8c2 assets/packages/assets/google_icon.svg,1740755612751,e08acff98ce88a250447229cee21ecdae27480ac800b1b4da44eecb48b88da3b assets/packages/assets/friends.svg,1738903832234,1ee30373884f25838c31f838cebc5380b6126831e920cf5bc7fbac2aa57db3df +assets/packages/assets/edit_pencil.svg,1751873154521,5fb0fa7d8b7affc52fba9ed4dfd7828d1478b5d1aad4f16a279281ce2d1ff19e assets/packages/assets/drag_indicator.svg,1738903832234,7f6340c5647dad5a0c507e6f1168a20907c47b7d5275d8496de67f0fd63716de assets/packages/assets/chevron_left.svg,1740755612751,8802af56fdfee2ecbe35180eadcba4f11b7569abc2c2574e41b7ff180e0c56f5 +assets/packages/assets/chevron_down.svg,1751873154521,beb5bba9c8beb3b0875bf5654d595a0d00c3c0354ef3d3d12bda863c0c49f7ca assets/packages/assets/check.svg,1738903832234,e676f27ee117041dedb876a9c543488d7cb67b631dd548d4aa1c4dd48c6e795a assets/packages/assets/character_greeting.svg,1740755612751,903498d2af556692923ea804f8da368a3d0e791ee66a8056a8ad1f5b42302187 -assets/packages/assets/character.png,1738903832234,35286d084ea575ff5850e8bbcf3d05ebe92fadf294461e207dbac059ebb16975 assets/packages/assets/bell.svg,1738903832233,49a4b438c7ea87905fe3ded57d50eef2f1d1cd4bfc211a3c3ad99203859be4eb +assets/packages/assets/bell-ringing.svg,1751874063686,0e894d7cbfed735c201d89eddd73431210f2e50dc98a0fd95e7f623912e06cd5 assets/packages/assets/arrow_right.svg,1738903832233,040f26c73d8bd55b2907501108164918edbe1d5fc161f5400b9b2eeeb502df0b -assets/assets/pubspec.yaml,1740755364270,97f7c5dd9c68dd4d7f2f8f9d70164b968cef244070ee02a85f5b217ca53b41ce -assets/assets/meatballs.svg,1740755364270,32314300150c2bbf11964bb161c1b56376cc720a347d0a282fe95bbb1ad6ea1a -assets/assets/google_icon.svg,1740755612751,e08acff98ce88a250447229cee21ecdae27480ac800b1b4da44eecb48b88da3b -assets/assets/friends.svg,1738903832234,1ee30373884f25838c31f838cebc5380b6126831e920cf5bc7fbac2aa57db3df -assets/assets/drag_indicator.svg,1738903832234,7f6340c5647dad5a0c507e6f1168a20907c47b7d5275d8496de67f0fd63716de -assets/assets/chevron_left.svg,1740755612751,8802af56fdfee2ecbe35180eadcba4f11b7569abc2c2574e41b7ff180e0c56f5 -assets/assets/check.svg,1738903832234,e676f27ee117041dedb876a9c543488d7cb67b631dd548d4aa1c4dd48c6e795a -assets/assets/character_greeting.svg,1740755612751,903498d2af556692923ea804f8da368a3d0e791ee66a8056a8ad1f5b42302187 -assets/assets/character.png,1738903832234,35286d084ea575ff5850e8bbcf3d05ebe92fadf294461e207dbac059ebb16975 -assets/assets/bell.svg,1738903832233,49a4b438c7ea87905fe3ded57d50eef2f1d1cd4bfc211a3c3ad99203859be4eb -assets/assets/arrow_right.svg,1738903832233,040f26c73d8bd55b2907501108164918edbe1d5fc161f5400b9b2eeeb502df0b +assets/packages/assets/Plus.svg,1750668902245,b6ac76bebf49483c61a15f030ce9b42c41b559a83f926f282a5998034fc7a2ef +assets/packages/assets/My.svg,1750668902245,c7e4ee520bbe25b85ceb14240bfec2e9df7d62970a7a3706b371c5decf69d968 +assets/packages/assets/Home.svg,1750668902245,ec7eca5316f5d7d03e38f35f238f5ac9083bf71a9988f658461e4e022798bcf6 +assets/packages/assets/fonts/Pretendard-Thin.ttf,1741271571730,08f0d2582e2d57a69251416419835211228f008ad5c5030e556d073e944a1163 +assets/packages/assets/fonts/Pretendard-SemiBold.ttf,1741271571725,4dd3c854bad5348ba2beb8da553aeafe1d3d47076cd967854a528731acdda82a +assets/packages/assets/fonts/Pretendard-Regular.ttf,1741271571719,5f0cf1bf0eb351550179a82dc7a9367ebab30004a353f7de0d681e171fe0c3d3 +assets/packages/assets/fonts/Pretendard-Medium.ttf,1741271571714,ab65081a45a0401fe472fe73e3d3c65c506371804b1f066739f7ecde276104b4 +assets/packages/assets/fonts/Pretendard-Light.ttf,1741271571708,d2c0b5af96e96d8063c08837230ea14b258c9b89b18c5efefe21658aedc01259 +assets/packages/assets/fonts/Pretendard-ExtraLight.ttf,1741271571702,bf25b1053065297c0cacfd770844f6b53a4564bbe2f5778e6553423712f06d87 +assets/packages/assets/fonts/Pretendard-ExtraBold.ttf,1741271571695,374f1cdec1c9872bfdabfc5049437dd6334dee93700538243ef573f3b735de04 +assets/packages/assets/fonts/Pretendard-Bold.ttf,1741271571690,2e40f7edb945eec3271f1e5cd938fe774adade44641e0715a89330354b8b5262 +assets/packages/assets/fonts/Pretendard-Black.ttf,1741271571685,d54873770d0faf69253bb90d4318993b837fd7b584833d375fb53fddf2182a57 +assets/packages/assets/characters/onboarding_character.svg,1743489251941,d7423b05fd5c5682f721ee5e366f0092ea8fd13f1794770c47b53c4f33bfd86c +assets/packages/assets/characters/character_whistle.svg,1751874063687,7feddbb3fbd19eea850ecc2c6b23bd0e58efaa7b397d651bb0c7c97923d62419 +assets/packages/assets/characters/character_late_earth.svg,1751874063687,946472332dff00e8d28859c050f00901dc6fce59708ef6e99bfadc9e52ae723b +assets/packages/assets/characters/character_headphone.svg,1751874063686,8820769698f302305ff1c159cfa1fdebb9a4d1b12e193ecb2cea836c61c17d93 +assets/packages/assets/characters/character.svg,1750668902246,464b1f16cb53180e813193883d6ab84af066193b746da7e468e57c8d6db1016c assets/assets/fonts/Pretendard-Thin.ttf,1741271571730,08f0d2582e2d57a69251416419835211228f008ad5c5030e556d073e944a1163 assets/assets/fonts/Pretendard-SemiBold.ttf,1741271571725,4dd3c854bad5348ba2beb8da553aeafe1d3d47076cd967854a528731acdda82a assets/assets/fonts/Pretendard-Regular.ttf,1741271571719,5f0cf1bf0eb351550179a82dc7a9367ebab30004a353f7de0d681e171fe0c3d3 @@ -53,16 +82,15 @@ assets/assets/fonts/Pretendard-ExtraLight.ttf,1741271571702,bf25b1053065297c0cac assets/assets/fonts/Pretendard-ExtraBold.ttf,1741271571695,374f1cdec1c9872bfdabfc5049437dd6334dee93700538243ef573f3b735de04 assets/assets/fonts/Pretendard-Bold.ttf,1741271571690,2e40f7edb945eec3271f1e5cd938fe774adade44641e0715a89330354b8b5262 assets/assets/fonts/Pretendard-Black.ttf,1741271571685,d54873770d0faf69253bb90d4318993b837fd7b584833d375fb53fddf2182a57 -version.json,1742196629388,3fe66f58c7b0080dde159d39cc063691b0918161056f5a917bf3094372849e2f -flutter_service_worker.js,1742196631024,702f2111014a58322d9348ae1347dc422ca892fb10869084a933b44abe544abd -flutter_bootstrap.js,1742196629054,4bf591df5ab527696b57c069974925265ec05303160fb0cf04391d21433af517 -index.html,1742196629058,8e245a51242bf7295809eb2acfe4d385ac43314cda8f950a671efc732f2389dd -assets/AssetManifest.json,1742196629484,047af0ade8f084f8d59e40e9dd3c5a2d3e1ffa3de23d50f9d4c03c4ed3b77b09 -assets/FontManifest.json,1742196629484,0c968932010df9e5202500a7acdd4f8448d421d4017ca6afaf4335c16dc951aa -favicon.ico,1742163336000,f9a33e18c8eda1a025b8bc80736ac4cb93ff348dc42f1dd19d34eb30080e4c73 -assets/AssetManifest.bin.json,1742196629484,964cf7d6b415bb1842182a8a79ab9d021ad14962a7a139633bd47a1a872677c1 -assets/AssetManifest.bin,1742196629484,010317c335c67cd05018616bd643931078fc91a96de7ed76e5544fe7ccdfb195 -assets/shaders/ink_sparkle.frag,1742196629588,80c6e65c75f1de434b1b22dba61e96ad82dba0f2fc5e8b3b59c2def46d794354 -assets/fonts/MaterialIcons-Regular.otf,1742196630435,ca9df6f14a20e3b4e1ae7b7857f56b0563ab90564b04633477e4242f948dce70 -assets/packages/cupertino_icons/assets/CupertinoIcons.ttf,1742196630435,53de5ef48304000a5bae3a08f9499510850cbb032372063e82f1f1dcd938f395 -assets/NOTICES,1742196629484,efb01c5cd600fe3ae72b5c7b44733ac570e80f528e4c1d207b16684e33e5f51d +version.json,1752492631935,3fe66f58c7b0080dde159d39cc063691b0918161056f5a917bf3094372849e2f +index.html,1752492631464,6b105ca8a67fd3db8921be5bfe26a8a75eb147dad4015c8a7af161f6e648a85e +flutter_bootstrap.js,1752492631450,17b8adfc6ec198ff3766c8fc0e9836dc18104c6af2ccc0754c41215963224389 +flutter_service_worker.js,1752492633737,ec3bdaa13bca1f5c07324b9773d41b4305a626ad037eeeb650c77f5c84dfe45e +assets/FontManifest.json,1752492632023,54c5688728a24562e288e535588428f46cae8ae083620677b3623e61776b4f3f +assets/AssetManifest.bin.json,1752492632023,6e0d2359eab69b0e75e7c7a03438add2ed0dcdebe2897f3a3e31befe05cb76cc +assets/AssetManifest.json,1752492632023,2c74d88153ec9425f4b2097ccd3446ee6c35e84d6925332415dced51bf0afada +assets/AssetManifest.bin,1752492632023,254e0919a1241f26abd472d313843cb1f28be084fde2b507405498bec49cdbd9 +assets/packages/cupertino_icons/assets/CupertinoIcons.ttf,1752492632919,12bc6bf55aad4657f62747b6c1c9b5c120a594ed3540db21729b6db3c847340d +assets/shaders/ink_sparkle.frag,1752492632104,80c6e65c75f1de434b1b22dba61e96ad82dba0f2fc5e8b3b59c2def46d794354 +assets/fonts/MaterialIcons-Regular.otf,1752492632919,9fd6dfb402eb47d98919d5fc0b5ff7fdcca2d7e8c4b66fa69ac9cabcb6f18af7 +assets/NOTICES,1752492632025,d73d4f8b973e02b39ee6db02af01aa00137f53ce4b1da8bf035fe67354ee7679 diff --git a/assets/characters/half_character.svg b/assets/characters/half_character.svg new file mode 100644 index 00000000..61869d73 --- /dev/null +++ b/assets/characters/half_character.svg @@ -0,0 +1,61 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/assets/profile.png b/assets/profile.png new file mode 100644 index 00000000..9cbf1e12 Binary files /dev/null and b/assets/profile.png differ diff --git a/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme b/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme index fc27324a..0663e871 100644 --- a/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme +++ b/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme @@ -44,6 +44,7 @@ buildConfiguration = "Debug" selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB" selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB" + customLLDBInitFile = "$(SRCROOT)/Flutter/ephemeral/flutter_lldbinit" shouldUseLaunchSchemeArgsEnv = "YES"> _requestNotificationPermission(); - -@JS() -external JSBoolean _isInStandaloneMode(); - -class JsInteropService { - static Future requestNotificationPermission() { - return _requestNotificationPermission() - .toDart - .then((jsString) => jsString.toString()); - } - - static bool isInStandaloneMode() { - return _isInStandaloneMode().toDart; - } -} +export 'js_interop_service_stub.dart' + if (dart.library.js_interop) 'js_interop_service_web.dart'; diff --git a/lib/core/services/js_interop_service_stub.dart b/lib/core/services/js_interop_service_stub.dart new file mode 100644 index 00000000..56605c65 --- /dev/null +++ b/lib/core/services/js_interop_service_stub.dart @@ -0,0 +1,9 @@ +class JsInteropService { + static Future requestNotificationPermission() async { + throw UnsupportedError('JsInteropService is only available on web'); + } + + static bool isInStandaloneMode() { + throw UnsupportedError('JsInteropService is only available on web'); + } +} diff --git a/lib/core/services/js_interop_service_web.dart b/lib/core/services/js_interop_service_web.dart new file mode 100644 index 00000000..1d9a136e --- /dev/null +++ b/lib/core/services/js_interop_service_web.dart @@ -0,0 +1,20 @@ +import 'dart:js_interop'; +import 'package:js/js.dart'; + +@JS() +external JSPromise _requestNotificationPermission(); + +@JS() +external JSBoolean _isInStandaloneMode(); + +class JsInteropService { + static Future requestNotificationPermission() { + return _requestNotificationPermission() + .toDart + .then((jsString) => jsString.toString()); + } + + static bool isInStandaloneMode() { + return _isInStandaloneMode().toDart; + } +} diff --git a/lib/l10n/app_en.arb b/lib/l10n/app_en.arb index b3f91256..f41bd8c0 100644 --- a/lib/l10n/app_en.arb +++ b/lib/l10n/app_en.arb @@ -274,5 +274,37 @@ "type": "int" } } + }, + "myPageTitle": "My Page", + "@myPageTitle": { + "description": "Title for the my page screen" + }, + "myAccount": "My Account", + "@myAccount": { + "description": "Title for the my account section" + }, + "appSettings": "App Settings", + "@appSettings": { + "description": "Title for the app settings section" + }, + "editDefaultPreparation": "Edit Default Preparation / Spare Time", + "@editDefaultPreparation": { + "description": "Setting tile for editing default preparation and spare time" + }, + "allowAppNotifications": "Allow App Notifications", + "@allowAppNotifications": { + "description": "Setting tile for allowing app notifications" + }, + "editSpareTime": "Edit spare time", + "@editSpareTime": { + "description": "Section title for editing spare time" + }, + "editPreparationTime": "Edit preparation time", + "@editPreparationTime": { + "description": "Section title for editing preparation time" + }, + "totalTime": "Total time: ", + "@totalTime": { + "description": "Label for total preparation time" } } \ No newline at end of file diff --git a/lib/l10n/app_ko.arb b/lib/l10n/app_ko.arb index 3cd05922..6e94fc09 100644 --- a/lib/l10n/app_ko.arb +++ b/lib/l10n/app_ko.arb @@ -62,5 +62,14 @@ "plus": "플러스", "schedule": "일정", "hourFormatted": "{count}시간", - "minuteFormatted": "{count}분" -} \ No newline at end of file + "minuteFormatted": "{count}분", + "myPageTitle": "마이페이지", + "myAccount": "내 계정", + "appSettings": "앱 설정", + "editDefaultPreparation": "기본 준비과정 / 여유시간 수정", + "allowAppNotifications": "앱 알림 허용" +, + "editSpareTime": "여유시간 수정", + "editPreparationTime": "준비시간 수정", + "totalTime": "총 시간: " +} \ No newline at end of file diff --git a/lib/l10n/app_localizations.dart b/lib/l10n/app_localizations.dart index bcae4261..0270853f 100644 --- a/lib/l10n/app_localizations.dart +++ b/lib/l10n/app_localizations.dart @@ -481,6 +481,54 @@ abstract class AppLocalizations { /// In en, this message translates to: /// **'{count,plural, =1{{count} minute} other{{count} minutes}}'** String minuteFormatted(int count); + + /// Title for the my page screen + /// + /// In en, this message translates to: + /// **'My Page'** + String get myPageTitle; + + /// Title for the my account section + /// + /// In en, this message translates to: + /// **'My Account'** + String get myAccount; + + /// Title for the app settings section + /// + /// In en, this message translates to: + /// **'App Settings'** + String get appSettings; + + /// Setting tile for editing default preparation and spare time + /// + /// In en, this message translates to: + /// **'Edit Default Preparation / Spare Time'** + String get editDefaultPreparation; + + /// Setting tile for allowing app notifications + /// + /// In en, this message translates to: + /// **'Allow App Notifications'** + String get allowAppNotifications; + + /// Section title for editing spare time + /// + /// In en, this message translates to: + /// **'Edit spare time'** + String get editSpareTime; + + /// Section title for editing preparation time + /// + /// In en, this message translates to: + /// **'Edit preparation time'** + String get editPreparationTime; + + /// Label for total preparation time + /// + /// In en, this message translates to: + /// **'Total time: '** + String get totalTime; } class _AppLocalizationsDelegate diff --git a/lib/l10n/app_localizations_en.dart b/lib/l10n/app_localizations_en.dart index fe4d5e47..0bb8846a 100644 --- a/lib/l10n/app_localizations_en.dart +++ b/lib/l10n/app_localizations_en.dart @@ -229,4 +229,28 @@ class AppLocalizationsEn extends AppLocalizations { ); return '$_temp0'; } + + @override + String get myPageTitle => 'My Page'; + + @override + String get myAccount => 'My Account'; + + @override + String get appSettings => 'App Settings'; + + @override + String get editDefaultPreparation => 'Edit Default Preparation / Spare Time'; + + @override + String get allowAppNotifications => 'Allow App Notifications'; + + @override + String get editSpareTime => 'Edit spare time'; + + @override + String get editPreparationTime => 'Edit preparation time'; + + @override + String get totalTime => 'Total time: '; } diff --git a/lib/l10n/app_localizations_ko.dart b/lib/l10n/app_localizations_ko.dart index ead61b7e..c39ccdb3 100644 --- a/lib/l10n/app_localizations_ko.dart +++ b/lib/l10n/app_localizations_ko.dart @@ -210,4 +210,28 @@ class AppLocalizationsKo extends AppLocalizations { String minuteFormatted(int count) { return '$count분'; } + + @override + String get myPageTitle => '마이페이지'; + + @override + String get myAccount => '내 계정'; + + @override + String get appSettings => '앱 설정'; + + @override + String get editDefaultPreparation => '기본 준비과정 / 여유시간 수정'; + + @override + String get allowAppNotifications => '앱 알림 허용'; + + @override + String get editSpareTime => '여유시간 수정'; + + @override + String get editPreparationTime => '준비시간 수정'; + + @override + String get totalTime => '총 시간: '; } diff --git a/lib/presentation/home/components/todays_schedule_tile.dart b/lib/presentation/home/components/todays_schedule_tile.dart index e8c8087a..47e5a237 100644 --- a/lib/presentation/home/components/todays_schedule_tile.dart +++ b/lib/presentation/home/components/todays_schedule_tile.dart @@ -12,7 +12,8 @@ class TodaysScheduleTile extends StatelessWidget { Widget _noSchedule(BuildContext context) { final theme = Theme.of(context); - return Center( + return Padding( + padding: const EdgeInsets.symmetric(horizontal: 11.0, vertical: 16.0), child: Text( AppLocalizations.of(context)!.noAppointments, style: theme.textTheme.bodyLarge?.copyWith( @@ -63,14 +64,10 @@ class TodaysScheduleTile extends StatelessWidget { color: schedule == null ? theme.colorScheme.surfaceContainerLow : theme.colorScheme.primaryContainer, - borderRadius: BorderRadius.circular(16), + borderRadius: BorderRadius.circular(8), ), width: double.infinity, - child: Padding( - padding: const EdgeInsets.symmetric(vertical: 6.5), - child: - schedule == null ? _noSchedule(context) : _scheduleExists(context), - ), + child: schedule == null ? _noSchedule(context) : _scheduleExists(context), ); } } diff --git a/lib/presentation/home/screens/home_screen_tmp.dart b/lib/presentation/home/screens/home_screen_tmp.dart index 51346e27..3d73acb8 100644 --- a/lib/presentation/home/screens/home_screen_tmp.dart +++ b/lib/presentation/home/screens/home_screen_tmp.dart @@ -46,8 +46,7 @@ class _HomeScreenTmpState extends State { Container( color: colorScheme.primary, padding: const EdgeInsets.only(top: 58.0), - child: Stack( - alignment: Alignment.bottomCenter, + child: Column( children: [ _CharacterSection(score: score), todaysScheduleOverlayBuilder(state), @@ -105,7 +104,8 @@ class _HomeScreenTmpState extends State { borderRadius: BorderRadius.circular(20), ), color: theme.colorScheme.surface, - elevation: 2, + elevation: 6, + shadowColor: Colors.black.withOpacity(0.4), child: Padding( padding: const EdgeInsets.all(20.0), child: Column( @@ -113,7 +113,7 @@ class _HomeScreenTmpState extends State { children: [ Text( AppLocalizations.of(context)!.todaysAppointments, - style: theme.textTheme.titleLarge, + style: theme.textTheme.titleMedium, ), SizedBox(height: 21.0), TodaysScheduleTile( @@ -307,8 +307,7 @@ class _CharacterSection extends StatelessWidget { @override Widget build(BuildContext context) { return Padding( - padding: const EdgeInsets.only(bottom: 40.0) + - EdgeInsets.symmetric(horizontal: 17.0), + padding: const EdgeInsets.symmetric(horizontal: 17.0), child: Row( crossAxisAlignment: CrossAxisAlignment.start, mainAxisAlignment: MainAxisAlignment.spaceBetween, @@ -380,9 +379,9 @@ class _Character extends StatelessWidget { Widget build(BuildContext context) { return SizedBox( width: 176, - height: 247.57, + height: 130, child: SvgPicture.asset( - 'characters/character.svg', + 'characters/half_character.svg', package: 'assets', ), ); diff --git a/lib/presentation/login/screens/sign_in_main_screen.dart b/lib/presentation/login/screens/sign_in_main_screen.dart index 8780f5fb..d514ce3f 100644 --- a/lib/presentation/login/screens/sign_in_main_screen.dart +++ b/lib/presentation/login/screens/sign_in_main_screen.dart @@ -37,7 +37,7 @@ class _SignInMainScreenState extends State { mainAxisSize: MainAxisSize.min, children: [ _Title(), - SizedBox(height: 24), + SizedBox(height: 48), _CharacterImage(), SizedBox(height: 24), GoogleSignInButton(), @@ -55,6 +55,7 @@ class _Title extends StatelessWidget { Widget build(BuildContext context) { final colorScheme = Theme.of(context).colorScheme; return Column( + spacing: 8, children: [ Text(AppLocalizations.of(context)!.appName, style: TextStyle( @@ -78,7 +79,7 @@ class _CharacterImage extends StatelessWidget { @override Widget build(BuildContext context) { return SizedBox( - height: 280, + height: 241, child: SvgPicture.asset( 'characters/character.svg', package: 'assets', diff --git a/lib/presentation/my_page/my_page_screen.dart b/lib/presentation/my_page/my_page_screen.dart new file mode 100644 index 00000000..8927c150 --- /dev/null +++ b/lib/presentation/my_page/my_page_screen.dart @@ -0,0 +1,158 @@ +import 'package:flutter/material.dart'; +import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:go_router/go_router.dart'; +import 'package:on_time_front/domain/entities/preparation_entity.dart'; +import 'package:on_time_front/l10n/app_localizations.dart'; +import 'package:on_time_front/presentation/app/bloc/app_bloc.dart'; + +class MyPageScreen extends StatelessWidget { + const MyPageScreen({super.key}); + + @override + Widget build(BuildContext context) { + return Scaffold( + backgroundColor: Theme.of(context).colorScheme.surfaceContainerLow, + appBar: AppBar( + title: Text(AppLocalizations.of(context)!.myPageTitle, + style: Theme.of(context).textTheme.titleLarge), + backgroundColor: Theme.of(context).colorScheme.surface, + ), + body: Column( + spacing: 12, + children: [ + _FrameView( + title: AppLocalizations.of(context)!.myAccount, + child: _MyAccountView()), + _FrameView( + title: AppLocalizations.of(context)!.appSettings, + child: Column( + spacing: 25, + children: [ + _SettingTile( + title: AppLocalizations.of(context)!.editDefaultPreparation, + onTap: () async { + final PreparationEntity? updatedPreparation = + await context.push('/defaultPreparationSpareTimeEdit'); + if (updatedPreparation != null) {} + }, + ), + _SettingTile( + title: AppLocalizations.of(context)!.allowAppNotifications, + onTap: () {}, + ), + ], + ), + ), + ], + ), + ); + } +} + +class _MyAccountView extends StatelessWidget { + const _MyAccountView(); + + @override + Widget build(BuildContext context) { + final textTheme = Theme.of(context).textTheme; + final colorScheme = Theme.of(context).colorScheme; + return BlocBuilder( + builder: (context, state) { + if (state.status == AppStatus.authenticated) { + final user = state.user.mapOrNull( + (user) => user, + empty: (_) => null, + ); + return Padding( + padding: const EdgeInsets.symmetric(horizontal: 10.0) + + EdgeInsets.only(bottom: 9), + child: Row( + spacing: 20, + children: [ + CircleAvatar( + radius: 30, + backgroundImage: Image.asset( + 'profile.png', + package: 'assets', + ).image, + ), + Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + Text(user!.name, style: textTheme.titleMedium), + Text(user.email, + style: textTheme.bodyMedium!.copyWith( + color: colorScheme.outline, + )), + ], + ), + ], + ), + ); + } + return const SizedBox.shrink(); + }, + ); + } +} + +class _FrameView extends StatelessWidget { + const _FrameView({ + required this.title, + required this.child, + }); + + final String title; + final Widget child; + + @override + Widget build(BuildContext context) { + final textTheme = Theme.of(context).textTheme; + final colorScheme = Theme.of(context).colorScheme; + return Container( + decoration: BoxDecoration( + color: Theme.of(context).colorScheme.surface, + ), + child: Padding( + padding: const EdgeInsets.symmetric(horizontal: 16, vertical: 19), + child: Column( + crossAxisAlignment: CrossAxisAlignment.start, + spacing: 25, + children: [ + Text(title, + style: + textTheme.bodyMedium!.copyWith(color: colorScheme.outline)), + child, + ], + ), + ), + ); + } +} + +class _SettingTile extends StatelessWidget { + const _SettingTile({ + required this.title, + required this.onTap, + }); + + final String title; + final VoidCallback onTap; + + @override + Widget build(BuildContext context) { + final textTheme = Theme.of(context).textTheme; + final colorScheme = Theme.of(context).colorScheme; + return InkWell( + onTap: onTap, + child: Row( + mainAxisAlignment: MainAxisAlignment.spaceBetween, + children: [ + Text(title, style: textTheme.bodyLarge), + Icon(Icons.arrow_forward_ios, + size: 16, color: colorScheme.outlineVariant), + ], + ), + ); + } +} diff --git a/lib/presentation/my_page/preparation_spare_time_edit/bloc/default_preparation_spare_time_form_bloc.dart b/lib/presentation/my_page/preparation_spare_time_edit/bloc/default_preparation_spare_time_form_bloc.dart new file mode 100644 index 00000000..a6237649 --- /dev/null +++ b/lib/presentation/my_page/preparation_spare_time_edit/bloc/default_preparation_spare_time_form_bloc.dart @@ -0,0 +1,96 @@ +import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:equatable/equatable.dart'; +import 'package:injectable/injectable.dart'; +import 'package:on_time_front/domain/entities/preparation_entity.dart'; +import 'package:on_time_front/domain/use-cases/get_default_preparation_use_case.dart'; +import 'package:on_time_front/domain/use-cases/onboard_use_case.dart'; + +part 'default_preparation_spare_time_form_event.dart'; +part 'default_preparation_spare_time_form_state.dart'; + +@injectable +class DefaultPreparationSpareTimeFormBloc extends Bloc< + DefaultPreparationSpareTimeFormEvent, + DefaultPreparationSpareTimeFormState> { + DefaultPreparationSpareTimeFormBloc( + this._getDefaultPreparationUseCase, + this._onboardUseCase, + ) : super(DefaultPreparationSpareTimeFormState()) { + on(_onFormEditRequested); + on(_onSpareTimeIncreased); + on(_onSpareTimeDecreased); + on(_onFormSubmitted); + } + + final GetDefaultPreparationUseCase _getDefaultPreparationUseCase; + final OnboardUseCase _onboardUseCase; + final Duration lowerBound = Duration(minutes: 10); + final Duration stepSize = Duration(minutes: 5); + + Future _onFormEditRequested(FormEditRequested event, + Emitter emit) async { + emit(state.copyWith( + status: DefaultPreparationSpareTimeStatus.loading, + )); + + final preparation = await _getDefaultPreparationUseCase(); + + emit(state.copyWith( + status: DefaultPreparationSpareTimeStatus.success, + preparation: preparation, + spareTime: event.spareTime, + )); + } + + void _onSpareTimeIncreased(SpareTimeIncreased event, + Emitter emit) { + final currentSpareTime = state.spareTime ?? Duration.zero; + final newSpareTime = currentSpareTime + stepSize; + + emit(state.copyWith( + spareTime: newSpareTime, + )); + } + + void _onSpareTimeDecreased(SpareTimeDecreased event, + Emitter emit) { + final currentSpareTime = state.spareTime ?? Duration.zero; + final newSpareTime = currentSpareTime - stepSize; + + if (newSpareTime >= lowerBound) { + emit(state.copyWith( + spareTime: newSpareTime, + )); + } + } + + Future _onFormSubmitted(FormSubmitted event, + Emitter emit) async { + if (state.spareTime == null) { + emit(state.copyWith( + status: DefaultPreparationSpareTimeStatus.error, + )); + return; + } + + emit(state.copyWith( + status: DefaultPreparationSpareTimeStatus.loading, + )); + + try { + await _onboardUseCase( + preparationEntity: event.preparation, + spareTime: state.spareTime!, + note: event.note, + ); + + emit(state.copyWith( + status: DefaultPreparationSpareTimeStatus.success, + )); + } catch (e) { + emit(state.copyWith( + status: DefaultPreparationSpareTimeStatus.error, + )); + } + } +} diff --git a/lib/presentation/my_page/preparation_spare_time_edit/bloc/default_preparation_spare_time_form_event.dart b/lib/presentation/my_page/preparation_spare_time_edit/bloc/default_preparation_spare_time_form_event.dart new file mode 100644 index 00000000..949b3fac --- /dev/null +++ b/lib/presentation/my_page/preparation_spare_time_edit/bloc/default_preparation_spare_time_form_event.dart @@ -0,0 +1,39 @@ +part of 'default_preparation_spare_time_form_bloc.dart'; + +class DefaultPreparationSpareTimeFormEvent extends Equatable { + const DefaultPreparationSpareTimeFormEvent(); + + @override + List get props => []; +} + +class FormEditRequested extends DefaultPreparationSpareTimeFormEvent { + const FormEditRequested({required this.spareTime}); + final Duration spareTime; + + @override + List get props => [spareTime]; +} + +class SpareTimeIncreased extends DefaultPreparationSpareTimeFormEvent { + const SpareTimeIncreased(); + + @override + List get props => []; +} + +class SpareTimeDecreased extends DefaultPreparationSpareTimeFormEvent { + const SpareTimeDecreased(); + + @override + List get props => []; +} + +class FormSubmitted extends DefaultPreparationSpareTimeFormEvent { + const FormSubmitted({required this.note, required this.preparation}); + final String note; + final PreparationEntity preparation; + + @override + List get props => [note]; +} diff --git a/lib/presentation/my_page/preparation_spare_time_edit/bloc/default_preparation_spare_time_form_state.dart b/lib/presentation/my_page/preparation_spare_time_edit/bloc/default_preparation_spare_time_form_state.dart new file mode 100644 index 00000000..97adef4f --- /dev/null +++ b/lib/presentation/my_page/preparation_spare_time_edit/bloc/default_preparation_spare_time_form_state.dart @@ -0,0 +1,34 @@ +part of 'default_preparation_spare_time_form_bloc.dart'; + +enum DefaultPreparationSpareTimeStatus { + initial, + loading, + success, + error, +} + +class DefaultPreparationSpareTimeFormState extends Equatable { + const DefaultPreparationSpareTimeFormState({ + this.status = DefaultPreparationSpareTimeStatus.initial, + this.spareTime, + this.preparation, + }); + final DefaultPreparationSpareTimeStatus status; + final Duration? spareTime; + final PreparationEntity? preparation; + + @override + List get props => [status, spareTime, preparation]; + + DefaultPreparationSpareTimeFormState copyWith({ + DefaultPreparationSpareTimeStatus? status, + Duration? spareTime, + PreparationEntity? preparation, + }) { + return DefaultPreparationSpareTimeFormState( + status: status ?? this.status, + spareTime: spareTime ?? this.spareTime, + preparation: preparation ?? this.preparation, + ); + } +} diff --git a/lib/presentation/my_page/preparation_spare_time_edit/preparation_spare_time_edit_screen.dart b/lib/presentation/my_page/preparation_spare_time_edit/preparation_spare_time_edit_screen.dart new file mode 100644 index 00000000..958f09fa --- /dev/null +++ b/lib/presentation/my_page/preparation_spare_time_edit/preparation_spare_time_edit_screen.dart @@ -0,0 +1,209 @@ +import 'package:flutter/material.dart'; +import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:go_router/go_router.dart'; +import 'package:on_time_front/core/di/di_setup.dart'; +import 'package:on_time_front/presentation/app/bloc/app_bloc.dart'; +import 'package:on_time_front/presentation/my_page/preparation_spare_time_edit/bloc/default_preparation_spare_time_form_bloc.dart'; +import 'package:on_time_front/l10n/app_localizations.dart'; +import 'package:on_time_front/presentation/schedule_create/schedule_spare_and_preparing_time/preparation_form/bloc/preparation_form_bloc.dart'; +import 'package:on_time_front/presentation/schedule_create/schedule_spare_and_preparing_time/preparation_form/components/preparation_form_create_list.dart'; +import 'package:on_time_front/presentation/shared/components/time_stepper.dart'; + +class PreparationSpareTimeEditScreen extends StatelessWidget { + const PreparationSpareTimeEditScreen({super.key}); + + @override + Widget build(BuildContext context) { + return BlocProvider( + create: (context) { + final spareTime = context + .read() + .state + .user + .mapOrNull((user) => user.spareTime) ?? + Duration.zero; + return getIt.get() + ..add(FormEditRequested(spareTime: spareTime)); + }, + child: const _PreparationSpareTimeEditView(), + ); + } +} + +class _PreparationSpareTimeEditView extends StatelessWidget { + const _PreparationSpareTimeEditView(); + + @override + Widget build(BuildContext context) { + return BlocBuilder( + builder: (context, state) { + if (state.status == DefaultPreparationSpareTimeStatus.success) { + return BlocProvider( + create: (context) => getIt.get() + ..add(PreparationFormEditRequested( + preparationEntity: state.preparation!)), + child: BlocBuilder( + builder: (context, state2) { + return Scaffold( + appBar: AppBar( + leading: IconButton( + icon: Icon( + Icons.arrow_back_ios_rounded, + color: Theme.of(context).colorScheme.outlineVariant, + ), + onPressed: () => context.pop(), + ), + title: Text( + AppLocalizations.of(context)!.editDefaultPreparation, + style: Theme.of(context).textTheme.titleLarge, + ), + actions: [ + TextButton( + onPressed: state2.isValid + ? () { + context + .read() + .add( + FormSubmitted( + note: '', + preparation: + state2.toPreparationEntity(), + ), + ); + context.pop(); + } + : null, + child: Text(AppLocalizations.of(context)!.ok), + ), + ], + bottom: const PreferredSize( + preferredSize: Size.fromHeight(33), + child: SizedBox(height: 33), + ), + ), + body: SafeArea( + child: Padding( + padding: const EdgeInsets.symmetric(horizontal: 16.0), + child: Column( + children: [ + SizedBox( + width: double.infinity, + child: + _SpareTimeSection(spareTime: state.spareTime!), + ), + SizedBox( + height: 42.0, + ), + Expanded( + child: _PreparationSection( + preparationNameState: state2, + ), + ), + ], + ), + ), + ), + ); + }, + ), + ); + } + + return const Center(child: CircularProgressIndicator()); + }, + ); + } +} + +class _SpareTimeSection extends StatelessWidget { + const _SpareTimeSection({required this.spareTime}); + + final Duration spareTime; + + @override + Widget build(BuildContext context) { + final textTheme = TextTheme.of(context); + return Column( + children: [ + SizedBox( + width: double.infinity, + child: Text( + AppLocalizations.of(context)!.editSpareTime, + textAlign: TextAlign.start, + style: textTheme.titleMedium, + ), + ), + SizedBox( + height: 24.0, + ), + TimeStepper( + onSpareTimeIncreased: () { + context.read().add( + const SpareTimeIncreased(), + ); + }, + onSpareTimeDecreased: () { + context.read().add( + const SpareTimeDecreased(), + ); + }, + lowerBound: Duration(minutes: 10), + value: spareTime, + ), + ], + ); + } +} + +class _PreparationSection extends StatelessWidget { + const _PreparationSection({required this.preparationNameState}); + + final PreparationFormState preparationNameState; + + @override + Widget build(BuildContext context) { + final textTheme = TextTheme.of(context); + return Column( + children: [ + SizedBox( + width: double.infinity, + child: Text( + AppLocalizations.of(context)!.editPreparationTime, + textAlign: TextAlign.start, + style: textTheme.titleMedium, + ), + ), + SizedBox( + height: 24.0, + ), + SizedBox( + width: double.infinity, + child: Padding( + padding: const EdgeInsets.only(bottom: 15.0), + child: Text( + AppLocalizations.of(context)!.totalTime, + textAlign: TextAlign.end, + ), + ), + ), + PreparationFormCreateList( + preparationNameState: preparationNameState, + onNameChanged: ({required int index, required String value}) { + context.read().add( + PreparationFormPreparationStepNameChanged( + index: index, + preparationStepName: value, + ), + ); + }, + onCreationRequested: () { + context.read().add( + const PreparationFormPreparationStepCreationRequested(), + ); + }, + ), + ], + ); + } +} diff --git a/lib/presentation/shared/components/calendar/centered_calendar_header.dart b/lib/presentation/shared/components/calendar/centered_calendar_header.dart index 7bd6822b..dab20a5d 100644 --- a/lib/presentation/shared/components/calendar/centered_calendar_header.dart +++ b/lib/presentation/shared/components/calendar/centered_calendar_header.dart @@ -22,6 +22,8 @@ class CenteredCalendarHeader extends StatelessWidget { @override Widget build(BuildContext context) { + final theme = Theme.of(context); + final textTheme = theme.textTheme; return Padding( padding: const EdgeInsets.symmetric(vertical: 4.0), child: Row( @@ -44,7 +46,7 @@ class CenteredCalendarHeader extends StatelessWidget { Text( DateFormat.yMMMM(AppLocalizations.of(context)!.localeName) .format(focusedMonth), - style: titleTextStyle, + style: textTheme.titleSmall, ), IconButton( padding: EdgeInsets.zero, diff --git a/lib/presentation/shared/router/go_router.dart b/lib/presentation/shared/router/go_router.dart index 1c0974b9..7ab56935 100644 --- a/lib/presentation/shared/router/go_router.dart +++ b/lib/presentation/shared/router/go_router.dart @@ -14,6 +14,8 @@ import 'package:on_time_front/presentation/calendar/screens/calendar_screen.dart import 'package:on_time_front/presentation/home/screens/home_screen_tmp.dart'; import 'package:on_time_front/presentation/login/screens/sign_in_main_screen.dart'; import 'package:on_time_front/presentation/moving/screens/moving_screen.dart'; +import 'package:on_time_front/presentation/my_page/my_page_screen.dart'; +import 'package:on_time_front/presentation/my_page/preparation_spare_time_edit/preparation_spare_time_edit_screen.dart'; import 'package:on_time_front/presentation/notification_allow/screens/notification_allow_screen.dart'; import 'package:on_time_front/presentation/onboarding/screens/onboarding_screen.dart'; import 'package:on_time_front/presentation/onboarding/screens/onboarding_start_screen.dart'; @@ -87,10 +89,14 @@ GoRouter goRouterConfig(AppBloc bloc) { ), GoRoute( path: '/myPage', - builder: (context, state) => Container(), + builder: (context, state) => MyPageScreen(), ), ], ), + GoRoute( + path: '/defaultPreparationSpareTimeEdit', + builder: (context, state) => PreparationSpareTimeEditScreen(), + ), GoRoute(path: '/signIn', builder: (context, state) => SignInMainScreen()), GoRoute(path: '/calendar', builder: (context, state) => CalendarScreen()), GoRoute( diff --git a/lib/presentation/shared/theme/text_theme.dart b/lib/presentation/shared/theme/text_theme.dart index bcaa61a5..176dd8f7 100644 --- a/lib/presentation/shared/theme/text_theme.dart +++ b/lib/presentation/shared/theme/text_theme.dart @@ -30,7 +30,7 @@ TextTheme _textTheme = TextTheme( ), titleMedium: TextStyle( fontSize: 18, - fontWeight: FontWeight.w500, + fontWeight: FontWeight.w600, color: _colorScheme.onSurface, height: 1.4, ), diff --git a/macos/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme b/macos/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme index c3f233b4..e87a57a8 100644 --- a/macos/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme +++ b/macos/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme @@ -59,6 +59,7 @@ ignoresPersistentStateOnLaunch = "NO" debugDocumentVersioning = "YES" debugServiceExtension = "internal" + enableGPUValidationMode = "1" allowLocationSimulation = "YES"> diff --git a/web/index.html b/web/index.html index fc5e20ab..0aaf1aa8 100644 --- a/web/index.html +++ b/web/index.html @@ -21,6 +21,10 @@ + + + + @@ -28,7 +32,8 @@ - + + @@ -40,6 +45,16 @@ on_time_front + + +