diff --git a/Rethread/.DS_Store b/Rethread/.DS_Store index ec8e23f..5e54b47 100644 Binary files a/Rethread/.DS_Store and b/Rethread/.DS_Store differ diff --git a/Rethread/Rethread.xcodeproj/project.pbxproj b/Rethread/Rethread.xcodeproj/project.pbxproj index bcda19b..d7d3de2 100644 --- a/Rethread/Rethread.xcodeproj/project.pbxproj +++ b/Rethread/Rethread.xcodeproj/project.pbxproj @@ -7,7 +7,27 @@ objects = { /* Begin PBXBuildFile section */ + 7C3B47132B853E520068DCCE /* AccountSettingsView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C3B47122B853E520068DCCE /* AccountSettingsView.swift */; }; + 7C6239982BB20CF800B4E2BF /* GenAccessoriesView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C6239972BB20CF800B4E2BF /* GenAccessoriesView.swift */; }; + 7C62399A2BB20D2900B4E2BF /* GenTopsView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C6239992BB20D2900B4E2BF /* GenTopsView.swift */; }; + 7C62399C2BB20D3600B4E2BF /* GenBottomsView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C62399B2BB20D3600B4E2BF /* GenBottomsView.swift */; }; + 7C62399E2BB20D3F00B4E2BF /* GenShoesView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C62399D2BB20D3F00B4E2BF /* GenShoesView.swift */; }; + 7C6748AB2B8D34E300F32B94 /* aboutArc'teryxBrandView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C6748AA2B8D34E300F32B94 /* aboutArc'teryxBrandView.swift */; }; + 7C83052A2BA3722A00FFD298 /* ReelView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C8305282BA3722A00FFD298 /* ReelView.swift */; }; + 7C83052B2BA3722A00FFD298 /* VideoPlayer.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C8305292BA3722A00FFD298 /* VideoPlayer.swift */; }; + 7C83052E2BA3725B00FFD298 /* ReelModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C83052C2BA3725B00FFD298 /* ReelModel.swift */; }; + 7C83052F2BA3725B00FFD298 /* MediaModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C83052D2BA3725B00FFD298 /* MediaModel.swift */; }; + 7C8305372BA374FC00FFD298 /* Reel4.MP4 in Resources */ = {isa = PBXBuildFile; fileRef = 7C8305332BA374FB00FFD298 /* Reel4.MP4 */; }; + 7C8305382BA374FC00FFD298 /* Reel3.MP4 in Resources */ = {isa = PBXBuildFile; fileRef = 7C8305342BA374FC00FFD298 /* Reel3.MP4 */; }; + 7C8305392BA374FC00FFD298 /* Reel2.mov in Resources */ = {isa = PBXBuildFile; fileRef = 7C8305352BA374FC00FFD298 /* Reel2.mov */; }; 7C8446E52B58CE8F00911C00 /* MapViewModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C8446E42B58CE8F00911C00 /* MapViewModel.swift */; }; + 7C9D4E262B85BC4E0034C385 /* AccountNotificationView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C9D4E252B85BC4E0034C385 /* AccountNotificationView.swift */; }; + 7CF454A92B86948C00DB3105 /* PhotoPickerModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7CF454A82B86948C00DB3105 /* PhotoPickerModel.swift */; }; + 7CF454AB2B8697B200DB3105 /* ScannerView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7CF454AA2B8697B200DB3105 /* ScannerView.swift */; }; + 7CF454AD2B87DCF400DB3105 /* aboutPatagoniaBrandView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7CF454AC2B87DCF400DB3105 /* aboutPatagoniaBrandView.swift */; }; + 7CF454AF2B87EBE600DB3105 /* FilterModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7CF454AE2B87EBE600DB3105 /* FilterModel.swift */; }; + 9807FC562BBD143900A2D727 /* FullVidView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9807FC552BBD143900A2D727 /* FullVidView.swift */; }; + 9807FC582BBD147B00A2D727 /* GoogleService-Info.plist in Resources */ = {isa = PBXBuildFile; fileRef = 9807FC572BBD147B00A2D727 /* GoogleService-Info.plist */; }; 983014C22B451A3E004A6A07 /* NavigationTransitions in Frameworks */ = {isa = PBXBuildFile; productRef = 983014C12B451A3E004A6A07 /* NavigationTransitions */; }; 983286B92B05698F00851B19 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 983286B82B05698F00851B19 /* Assets.xcassets */; }; 983286BC2B05698F00851B19 /* Preview Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 983286BB2B05698F00851B19 /* Preview Assets.xcassets */; }; @@ -15,7 +35,6 @@ 983286D02B05698F00851B19 /* RethreadUITests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 983286CF2B05698F00851B19 /* RethreadUITests.swift */; }; 983286D22B05698F00851B19 /* RethreadUITestsLaunchTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 983286D12B05698F00851B19 /* RethreadUITestsLaunchTests.swift */; }; 98434A5D2B63342700F81127 /* ContentView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98434A5C2B63342700F81127 /* ContentView.swift */; }; - 984674952B747FD200AFB77A /* GoogleService-Info.plist in Resources */ = {isa = PBXBuildFile; fileRef = 984674942B747FD200AFB77A /* GoogleService-Info.plist */; }; 985674F12B663E0D003FA5A0 /* FirebaseAuth in Frameworks */ = {isa = PBXBuildFile; productRef = 985674F02B663E0D003FA5A0 /* FirebaseAuth */; }; 985674F32B663E0D003FA5A0 /* FirebaseFirestore in Frameworks */ = {isa = PBXBuildFile; productRef = 985674F22B663E0D003FA5A0 /* FirebaseFirestore */; }; 985674F52B663E0D003FA5A0 /* FirebaseFirestoreSwift in Frameworks */ = {isa = PBXBuildFile; productRef = 985674F42B663E0D003FA5A0 /* FirebaseFirestoreSwift */; }; @@ -28,13 +47,12 @@ 98BBA11E2B68A6A100003AC2 /* VerificationView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1102B68A6A100003AC2 /* VerificationView.swift */; }; 98BBA11F2B68A6A100003AC2 /* ProductView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1112B68A6A100003AC2 /* ProductView.swift */; }; 98BBA1202B68A6A100003AC2 /* MapView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1122B68A6A100003AC2 /* MapView.swift */; }; - 98BBA1212B68A6A100003AC2 /* HomeView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1132B68A6A100003AC2 /* HomeView.swift */; }; + 98BBA1212B68A6A100003AC2 /* MainView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1132B68A6A100003AC2 /* MainView.swift */; }; 98BBA1222B68A6A100003AC2 /* testest.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1142B68A6A100003AC2 /* testest.swift */; }; 98BBA1232B68A6A100003AC2 /* WelcomeView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1152B68A6A100003AC2 /* WelcomeView.swift */; }; 98BBA1242B68A6A100003AC2 /* SignInView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1162B68A6A100003AC2 /* SignInView.swift */; }; 98BBA1252B68A6A100003AC2 /* SwiftUIView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1172B68A6A100003AC2 /* SwiftUIView.swift */; }; - 98BBA1262B68A6A100003AC2 /* ClothingItemView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1182B68A6A100003AC2 /* ClothingItemView.swift */; }; - 98BBA1272B68A6A100003AC2 /* MainView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1192B68A6A100003AC2 /* MainView.swift */; }; + 98BBA1272B68A6A100003AC2 /* AuthenticationView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA1192B68A6A100003AC2 /* AuthenticationView.swift */; }; 98BBA1282B68A6A100003AC2 /* SignUpView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA11A2B68A6A100003AC2 /* SignUpView.swift */; }; 98BBA1292B68A6A100003AC2 /* OnboardingView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA11B2B68A6A100003AC2 /* OnboardingView.swift */; }; 98BBA12B2B68A75200003AC2 /* OnboardingApp.swift in Sources */ = {isa = PBXBuildFile; fileRef = 98BBA12A2B68A75200003AC2 /* OnboardingApp.swift */; }; @@ -66,7 +84,31 @@ /* End PBXContainerItemProxy section */ /* Begin PBXFileReference section */ + 7C3B47122B853E520068DCCE /* AccountSettingsView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AccountSettingsView.swift; sourceTree = ""; }; + 7C6239972BB20CF800B4E2BF /* GenAccessoriesView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = GenAccessoriesView.swift; sourceTree = ""; }; + 7C6239992BB20D2900B4E2BF /* GenTopsView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = GenTopsView.swift; sourceTree = ""; }; + 7C62399B2BB20D3600B4E2BF /* GenBottomsView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = GenBottomsView.swift; sourceTree = ""; }; + 7C62399D2BB20D3F00B4E2BF /* GenShoesView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = GenShoesView.swift; sourceTree = ""; }; + 7C6748AA2B8D34E300F32B94 /* aboutArc'teryxBrandView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "aboutArc'teryxBrandView.swift"; sourceTree = ""; }; + 7C8305282BA3722A00FFD298 /* ReelView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ReelView.swift; sourceTree = ""; }; + 7C8305292BA3722A00FFD298 /* VideoPlayer.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = VideoPlayer.swift; sourceTree = ""; }; + 7C83052C2BA3725B00FFD298 /* ReelModel.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ReelModel.swift; sourceTree = ""; }; + 7C83052D2BA3725B00FFD298 /* MediaModel.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MediaModel.swift; sourceTree = ""; }; + 7C8305322BA374FB00FFD298 /* Reel5.MP4 */ = {isa = PBXFileReference; lastKnownFileType = file; path = Reel5.MP4; sourceTree = ""; }; + 7C8305332BA374FB00FFD298 /* Reel4.MP4 */ = {isa = PBXFileReference; lastKnownFileType = file; path = Reel4.MP4; sourceTree = ""; }; + 7C8305342BA374FC00FFD298 /* Reel3.MP4 */ = {isa = PBXFileReference; lastKnownFileType = file; path = Reel3.MP4; sourceTree = ""; }; + 7C8305352BA374FC00FFD298 /* Reel2.mov */ = {isa = PBXFileReference; lastKnownFileType = video.quicktime; path = Reel2.mov; sourceTree = ""; }; + 7C83053A2BA37C0400FFD298 /* sus2.mp4 */ = {isa = PBXFileReference; lastKnownFileType = file; path = sus2.mp4; sourceTree = ""; }; + 7C83053B2BA37C0400FFD298 /* sus1.mp4 */ = {isa = PBXFileReference; lastKnownFileType = file; name = sus1.mp4; path = Rethread/sus1.mp4; sourceTree = SOURCE_ROOT; }; + 7C83053C2BA37C0400FFD298 /* sus3.mp4 */ = {isa = PBXFileReference; lastKnownFileType = file; path = sus3.mp4; sourceTree = ""; }; 7C8446E42B58CE8F00911C00 /* MapViewModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MapViewModel.swift; sourceTree = ""; }; + 7C9D4E252B85BC4E0034C385 /* AccountNotificationView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AccountNotificationView.swift; sourceTree = ""; }; + 7CF454A82B86948C00DB3105 /* PhotoPickerModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PhotoPickerModel.swift; sourceTree = ""; }; + 7CF454AA2B8697B200DB3105 /* ScannerView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ScannerView.swift; sourceTree = ""; }; + 7CF454AC2B87DCF400DB3105 /* aboutPatagoniaBrandView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = aboutPatagoniaBrandView.swift; sourceTree = ""; }; + 7CF454AE2B87EBE600DB3105 /* FilterModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FilterModel.swift; sourceTree = ""; }; + 9807FC552BBD143900A2D727 /* FullVidView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FullVidView.swift; sourceTree = ""; }; + 9807FC572BBD147B00A2D727 /* GoogleService-Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = "GoogleService-Info.plist"; sourceTree = ""; }; 983286B12B05698E00851B19 /* Rethread.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Rethread.app; sourceTree = BUILT_PRODUCTS_DIR; }; 983286B82B05698F00851B19 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; 983286BB2B05698F00851B19 /* Preview Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = "Preview Assets.xcassets"; sourceTree = ""; }; @@ -77,7 +119,7 @@ 983286D12B05698F00851B19 /* RethreadUITestsLaunchTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RethreadUITestsLaunchTests.swift; sourceTree = ""; }; 983D40FA2B68D13E00905D4E /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist; path = Info.plist; sourceTree = ""; }; 98434A5C2B63342700F81127 /* ContentView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ContentView.swift; sourceTree = ""; }; - 984674942B747FD200AFB77A /* GoogleService-Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = "GoogleService-Info.plist"; sourceTree = ""; }; + 98547AB42BA799900098C9C2 /* Rethread.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = Rethread.entitlements; sourceTree = ""; }; 9868A7DD2B1FAE780063D9BA /* ButtonStyles.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ButtonStyles.swift; sourceTree = ""; }; 988A0F982B3C112300ACDC90 /* DatePickerModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DatePickerModel.swift; sourceTree = ""; }; 9897C7722B3E6C4000EDE9D9 /* CustomDropdownMenu.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CustomDropdownMenu.swift; sourceTree = ""; }; @@ -86,13 +128,12 @@ 98BBA1102B68A6A100003AC2 /* VerificationView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = VerificationView.swift; sourceTree = ""; }; 98BBA1112B68A6A100003AC2 /* ProductView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ProductView.swift; sourceTree = ""; }; 98BBA1122B68A6A100003AC2 /* MapView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MapView.swift; sourceTree = ""; }; - 98BBA1132B68A6A100003AC2 /* HomeView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = HomeView.swift; sourceTree = ""; }; + 98BBA1132B68A6A100003AC2 /* MainView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MainView.swift; sourceTree = ""; }; 98BBA1142B68A6A100003AC2 /* testest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = testest.swift; sourceTree = ""; }; 98BBA1152B68A6A100003AC2 /* WelcomeView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = WelcomeView.swift; sourceTree = ""; }; 98BBA1162B68A6A100003AC2 /* SignInView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = SignInView.swift; sourceTree = ""; }; 98BBA1172B68A6A100003AC2 /* SwiftUIView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = SwiftUIView.swift; sourceTree = ""; }; - 98BBA1182B68A6A100003AC2 /* ClothingItemView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ClothingItemView.swift; sourceTree = ""; }; - 98BBA1192B68A6A100003AC2 /* MainView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MainView.swift; sourceTree = ""; }; + 98BBA1192B68A6A100003AC2 /* AuthenticationView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = AuthenticationView.swift; sourceTree = ""; }; 98BBA11A2B68A6A100003AC2 /* SignUpView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = SignUpView.swift; sourceTree = ""; }; 98BBA11B2B68A6A100003AC2 /* OnboardingView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = OnboardingView.swift; sourceTree = ""; }; 98BBA12A2B68A75200003AC2 /* OnboardingApp.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = OnboardingApp.swift; sourceTree = ""; }; @@ -139,9 +180,13 @@ 7C9AA2CC2B0EC02600EF6F36 /* Models */ = { isa = PBXGroup; children = ( + 7C83052D2BA3725B00FFD298 /* MediaModel.swift */, + 7C83052C2BA3725B00FFD298 /* ReelModel.swift */, 988A0F982B3C112300ACDC90 /* DatePickerModel.swift */, 98F525CD2B46A96F00CCAD78 /* TermsAndConditions.swift */, 7C8446E42B58CE8F00911C00 /* MapViewModel.swift */, + 7CF454A82B86948C00DB3105 /* PhotoPickerModel.swift */, + 7CF454AE2B87EBE600DB3105 /* FilterModel.swift */, ); path = Models; sourceTree = ""; @@ -166,7 +211,6 @@ isa = PBXGroup; children = ( 983286B32B05698E00851B19 /* Rethread */, - 984674942B747FD200AFB77A /* GoogleService-Info.plist */, 983286C42B05698F00851B19 /* RethreadTests */, 983286CE2B05698F00851B19 /* RethreadUITests */, 983286B22B05698E00851B19 /* Products */, @@ -187,6 +231,8 @@ 983286B32B05698E00851B19 /* Rethread */ = { isa = PBXGroup; children = ( + 9807FC572BBD147B00A2D727 /* GoogleService-Info.plist */, + 98547AB42BA799900098C9C2 /* Rethread.entitlements */, 983D40FA2B68D13E00905D4E /* Info.plist */, 7C9AA2D42B0ECADF00EF6F36 /* Styles */, 980DACBB2B71E7110008B88A /* Extensions */, @@ -197,6 +243,13 @@ 98BBA10D2B68A6A100003AC2 /* Views */, 98EA47322B605E5200AA2E8F /* Core */, 983286B82B05698F00851B19 /* Assets.xcassets */, + 7C83053B2BA37C0400FFD298 /* sus1.mp4 */, + 7C83053A2BA37C0400FFD298 /* sus2.mp4 */, + 7C83053C2BA37C0400FFD298 /* sus3.mp4 */, + 7C8305352BA374FC00FFD298 /* Reel2.mov */, + 7C8305342BA374FC00FFD298 /* Reel3.MP4 */, + 7C8305332BA374FB00FFD298 /* Reel4.MP4 */, + 7C8305322BA374FB00FFD298 /* Reel5.MP4 */, 983286BA2B05698F00851B19 /* Preview Content */, ); path = Rethread; @@ -247,19 +300,30 @@ 98BBA10D2B68A6A100003AC2 /* Views */ = { isa = PBXGroup; children = ( + 7C8305282BA3722A00FFD298 /* ReelView.swift */, + 7C8305292BA3722A00FFD298 /* VideoPlayer.swift */, 98BBA10F2B68A6A100003AC2 /* ProfileView.swift */, + 7C6239972BB20CF800B4E2BF /* GenAccessoriesView.swift */, + 7C3B47122B853E520068DCCE /* AccountSettingsView.swift */, + 7C9D4E252B85BC4E0034C385 /* AccountNotificationView.swift */, 98BBA1102B68A6A100003AC2 /* VerificationView.swift */, + 7CF454AC2B87DCF400DB3105 /* aboutPatagoniaBrandView.swift */, + 7C6748AA2B8D34E300F32B94 /* aboutArc'teryxBrandView.swift */, 98BBA1112B68A6A100003AC2 /* ProductView.swift */, 98BBA1122B68A6A100003AC2 /* MapView.swift */, - 98BBA1132B68A6A100003AC2 /* HomeView.swift */, + 98BBA1132B68A6A100003AC2 /* MainView.swift */, + 7C6239992BB20D2900B4E2BF /* GenTopsView.swift */, + 7C62399B2BB20D3600B4E2BF /* GenBottomsView.swift */, + 7C62399D2BB20D3F00B4E2BF /* GenShoesView.swift */, 98BBA1142B68A6A100003AC2 /* testest.swift */, 98BBA1152B68A6A100003AC2 /* WelcomeView.swift */, 98BBA1162B68A6A100003AC2 /* SignInView.swift */, 98BBA1172B68A6A100003AC2 /* SwiftUIView.swift */, - 98BBA1182B68A6A100003AC2 /* ClothingItemView.swift */, - 98BBA1192B68A6A100003AC2 /* MainView.swift */, + 98BBA1192B68A6A100003AC2 /* AuthenticationView.swift */, 98BBA11A2B68A6A100003AC2 /* SignUpView.swift */, 98BBA11B2B68A6A100003AC2 /* OnboardingView.swift */, + 7CF454AA2B8697B200DB3105 /* ScannerView.swift */, + 9807FC552BBD143900A2D727 /* FullVidView.swift */, ); path = Views; sourceTree = ""; @@ -409,9 +473,12 @@ isa = PBXResourcesBuildPhase; buildActionMask = 2147483647; files = ( + 7C8305392BA374FC00FFD298 /* Reel2.mov in Resources */, 983286BC2B05698F00851B19 /* Preview Assets.xcassets in Resources */, - 984674952B747FD200AFB77A /* GoogleService-Info.plist in Resources */, 983286B92B05698F00851B19 /* Assets.xcassets in Resources */, + 7C8305372BA374FC00FFD298 /* Reel4.MP4 in Resources */, + 7C8305382BA374FC00FFD298 /* Reel3.MP4 in Resources */, + 9807FC582BBD147B00A2D727 /* GoogleService-Info.plist in Resources */, ); runOnlyForDeploymentPostprocessing = 0; }; @@ -438,29 +505,44 @@ files = ( 98BBA1292B68A6A100003AC2 /* OnboardingView.swift in Sources */, 98BBA1222B68A6A100003AC2 /* testest.swift in Sources */, - 98BBA1262B68A6A100003AC2 /* ClothingItemView.swift in Sources */, 9868A7DE2B1FAE780063D9BA /* ButtonStyles.swift in Sources */, + 7CF454AF2B87EBE600DB3105 /* FilterModel.swift in Sources */, 98EA47352B6065C600AA2E8F /* User.swift in Sources */, 98BBA12D2B68ACBF00003AC2 /* Verification.swift in Sources */, + 7CF454A92B86948C00DB3105 /* PhotoPickerModel.swift in Sources */, 98A1838C2B38D32A001E324A /* ColorPalette.swift in Sources */, 98BBA12B2B68A75200003AC2 /* OnboardingApp.swift in Sources */, + 7CF454AB2B8697B200DB3105 /* ScannerView.swift in Sources */, 98BBA1242B68A6A100003AC2 /* SignInView.swift in Sources */, + 7C6748AB2B8D34E300F32B94 /* aboutArc'teryxBrandView.swift in Sources */, 98F541222B60A2CC00B6AA04 /* AuthViewModel.swift in Sources */, + 7CF454AD2B87DCF400DB3105 /* aboutPatagoniaBrandView.swift in Sources */, + 7C62399A2BB20D2900B4E2BF /* GenTopsView.swift in Sources */, + 7C62399E2BB20D3F00B4E2BF /* GenShoesView.swift in Sources */, + 7C6239982BB20CF800B4E2BF /* GenAccessoriesView.swift in Sources */, 98F525CE2B46A96F00CCAD78 /* TermsAndConditions.swift in Sources */, + 7C9D4E262B85BC4E0034C385 /* AccountNotificationView.swift in Sources */, 98F525C92B469BBD00CCAD78 /* PlayerView.swift in Sources */, 98F525CB2B469BEB00CCAD78 /* UIPlayerView.swift in Sources */, 98BBA1232B68A6A100003AC2 /* WelcomeView.swift in Sources */, 98BBA11D2B68A6A100003AC2 /* ProfileView.swift in Sources */, + 7C83052A2BA3722A00FFD298 /* ReelView.swift in Sources */, + 7C83052F2BA3725B00FFD298 /* MediaModel.swift in Sources */, + 7C83052B2BA3722A00FFD298 /* VideoPlayer.swift in Sources */, 98434A5D2B63342700F81127 /* ContentView.swift in Sources */, 988A0F992B3C112300ACDC90 /* DatePickerModel.swift in Sources */, 9897C7732B3E6C4000EDE9D9 /* CustomDropdownMenu.swift in Sources */, - 98BBA1272B68A6A100003AC2 /* MainView.swift in Sources */, - 98BBA1212B68A6A100003AC2 /* HomeView.swift in Sources */, + 98BBA1272B68A6A100003AC2 /* AuthenticationView.swift in Sources */, + 98BBA1212B68A6A100003AC2 /* MainView.swift in Sources */, + 9807FC562BBD143900A2D727 /* FullVidView.swift in Sources */, + 7C83052E2BA3725B00FFD298 /* ReelModel.swift in Sources */, 98BBA1252B68A6A100003AC2 /* SwiftUIView.swift in Sources */, + 7C3B47132B853E520068DCCE /* AccountSettingsView.swift in Sources */, 98BBA11E2B68A6A100003AC2 /* VerificationView.swift in Sources */, 98D04FFF2B78763C00889156 /* CustomField.swift in Sources */, 98BBA11F2B68A6A100003AC2 /* ProductView.swift in Sources */, 98BBA1282B68A6A100003AC2 /* SignUpView.swift in Sources */, + 7C62399C2BB20D3600B4E2BF /* GenBottomsView.swift in Sources */, 98BBA1202B68A6A100003AC2 /* MapView.swift in Sources */, 7C8446E52B58CE8F00911C00 /* MapViewModel.swift in Sources */, ); @@ -624,27 +706,32 @@ ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor; CLANG_ENABLE_MODULES = YES; + CODE_SIGN_ENTITLEMENTS = Rethread/Rethread.entitlements; + CODE_SIGN_IDENTITY = "Apple Development"; CODE_SIGN_STYLE = Automatic; CURRENT_PROJECT_VERSION = 1; DEVELOPMENT_ASSET_PATHS = "\"Rethread/Preview Content\""; - DEVELOPMENT_TEAM = 4GW9NWA7H9; + DEVELOPMENT_TEAM = F599YAW8NA; ENABLE_PREVIEWS = YES; GENERATE_INFOPLIST_FILE = YES; INFOPLIST_FILE = Rethread/Info.plist; + INFOPLIST_KEY_NSCameraUsageDescription = "reThread needs to acess your camera to in order to take photos"; INFOPLIST_KEY_NSLocationWhenInUseUsageDescription = "Rethread needs your location"; INFOPLIST_KEY_UIApplicationSceneManifest_Generation = YES; INFOPLIST_KEY_UIApplicationSupportsIndirectInputEvents = YES; INFOPLIST_KEY_UILaunchScreen_Generation = YES; INFOPLIST_KEY_UISupportedInterfaceOrientations_iPad = "UIInterfaceOrientationPortrait UIInterfaceOrientationPortraitUpsideDown UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight"; INFOPLIST_KEY_UISupportedInterfaceOrientations_iPhone = "UIInterfaceOrientationPortrait UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight"; + INFOPLIST_KEY_UIUserInterfaceStyle = Light; IPHONEOS_DEPLOYMENT_TARGET = 17.0; LD_RUNPATH_SEARCH_PATHS = ( "$(inherited)", "@executable_path/Frameworks", ); MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = techstart.Rethread2; + PRODUCT_BUNDLE_IDENTIFIER = com.techstart.rethread; PRODUCT_NAME = "$(TARGET_NAME)"; + PROVISIONING_PROFILE_SPECIFIER = ""; SWIFT_EMIT_LOC_STRINGS = YES; SWIFT_OPTIMIZATION_LEVEL = "-Onone"; SWIFT_VERSION = 5.0; @@ -658,27 +745,32 @@ ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor; CLANG_ENABLE_MODULES = YES; + CODE_SIGN_ENTITLEMENTS = Rethread/Rethread.entitlements; + CODE_SIGN_IDENTITY = "Apple Development"; CODE_SIGN_STYLE = Automatic; CURRENT_PROJECT_VERSION = 1; DEVELOPMENT_ASSET_PATHS = "\"Rethread/Preview Content\""; - DEVELOPMENT_TEAM = 4GW9NWA7H9; + DEVELOPMENT_TEAM = F599YAW8NA; ENABLE_PREVIEWS = YES; GENERATE_INFOPLIST_FILE = YES; INFOPLIST_FILE = Rethread/Info.plist; + INFOPLIST_KEY_NSCameraUsageDescription = "reThread needs to acess your camera to in order to take photos"; INFOPLIST_KEY_NSLocationWhenInUseUsageDescription = "Rethread needs your location"; INFOPLIST_KEY_UIApplicationSceneManifest_Generation = YES; INFOPLIST_KEY_UIApplicationSupportsIndirectInputEvents = YES; INFOPLIST_KEY_UILaunchScreen_Generation = YES; INFOPLIST_KEY_UISupportedInterfaceOrientations_iPad = "UIInterfaceOrientationPortrait UIInterfaceOrientationPortraitUpsideDown UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight"; INFOPLIST_KEY_UISupportedInterfaceOrientations_iPhone = "UIInterfaceOrientationPortrait UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight"; + INFOPLIST_KEY_UIUserInterfaceStyle = Light; IPHONEOS_DEPLOYMENT_TARGET = 17.0; LD_RUNPATH_SEARCH_PATHS = ( "$(inherited)", "@executable_path/Frameworks", ); MARKETING_VERSION = 1.0; - PRODUCT_BUNDLE_IDENTIFIER = techstart.Rethread2; + PRODUCT_BUNDLE_IDENTIFIER = com.techstart.rethread; PRODUCT_NAME = "$(TARGET_NAME)"; + PROVISIONING_PROFILE_SPECIFIER = ""; SWIFT_EMIT_LOC_STRINGS = YES; SWIFT_VERSION = 5.0; TARGETED_DEVICE_FAMILY = "1,2"; diff --git a/Rethread/Rethread/.DS_Store b/Rethread/Rethread/.DS_Store index eb14a59..e477519 100644 Binary files a/Rethread/Rethread/.DS_Store and b/Rethread/Rethread/.DS_Store differ diff --git a/Rethread/Rethread/Assets.xcassets/Arcteryx.imageset/Arcteryx.png b/Rethread/Rethread/Assets.xcassets/Arcteryx.imageset/Arcteryx.png new file mode 100644 index 0000000..7540df1 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/Arcteryx.imageset/Arcteryx.png differ diff --git a/Rethread/Rethread/Assets.xcassets/Arcteryx.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/Arcteryx.imageset/Contents.json new file mode 100644 index 0000000..7d9cf44 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/Arcteryx.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "Arcteryx.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/BETAJACKETMENS.imageset/BETAJACKET MEN'S.png b/Rethread/Rethread/Assets.xcassets/BETAJACKETMENS.imageset/BETAJACKET MEN'S.png new file mode 100644 index 0000000..3b2b248 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/BETAJACKETMENS.imageset/BETAJACKET MEN'S.png differ diff --git a/Rethread/Rethread/Assets.xcassets/BETAJACKETMENS.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/BETAJACKETMENS.imageset/Contents.json new file mode 100644 index 0000000..e1e0523 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/BETAJACKETMENS.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "BETAJACKET MEN'S.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/Image.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/Image.imageset/Contents.json new file mode 100644 index 0000000..3444f35 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/Image.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "download.jpg", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/Image.imageset/download.jpg b/Rethread/Rethread/Assets.xcassets/Image.imageset/download.jpg new file mode 100644 index 0000000..d9bf8c3 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/Image.imageset/download.jpg differ diff --git a/Rethread/Rethread/Assets.xcassets/KOTN.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/KOTN.imageset/Contents.json new file mode 100644 index 0000000..ceecd88 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/KOTN.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "KOTN.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/KOTN.imageset/KOTN.png b/Rethread/Rethread/Assets.xcassets/KOTN.imageset/KOTN.png new file mode 100644 index 0000000..05bba6c Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/KOTN.imageset/KOTN.png differ diff --git a/Rethread/Rethread/Assets.xcassets/Patagonia.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/Patagonia.imageset/Contents.json new file mode 100644 index 0000000..6f6ac87 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/Patagonia.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "Patagonia.jpeg", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/Patagonia.imageset/Patagonia.jpeg b/Rethread/Rethread/Assets.xcassets/Patagonia.imageset/Patagonia.jpeg new file mode 100644 index 0000000..4be8988 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/Patagonia.imageset/Patagonia.jpeg differ diff --git a/Rethread/Rethread/Assets.xcassets/Reel2.dataset/Contents.json b/Rethread/Rethread/Assets.xcassets/Reel2.dataset/Contents.json new file mode 100644 index 0000000..208be05 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/Reel2.dataset/Contents.json @@ -0,0 +1,12 @@ +{ + "data" : [ + { + "filename" : "Reel2.mov", + "idiom" : "universal" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/Reel2.dataset/Reel2.mov b/Rethread/Rethread/Assets.xcassets/Reel2.dataset/Reel2.mov new file mode 100644 index 0000000..55dac15 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/Reel2.dataset/Reel2.mov differ diff --git a/Rethread/Rethread/Assets.xcassets/Reel3.dataset/Contents.json b/Rethread/Rethread/Assets.xcassets/Reel3.dataset/Contents.json new file mode 100644 index 0000000..aee8436 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/Reel3.dataset/Contents.json @@ -0,0 +1,12 @@ +{ + "data" : [ + { + "filename" : "Reel3.MP4", + "idiom" : "universal" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/Reel3.dataset/Reel3.MP4 b/Rethread/Rethread/Assets.xcassets/Reel3.dataset/Reel3.MP4 new file mode 100644 index 0000000..c906218 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/Reel3.dataset/Reel3.MP4 differ diff --git a/Rethread/Rethread/Assets.xcassets/Reel4.dataset/Contents.json b/Rethread/Rethread/Assets.xcassets/Reel4.dataset/Contents.json new file mode 100644 index 0000000..f62f891 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/Reel4.dataset/Contents.json @@ -0,0 +1,12 @@ +{ + "data" : [ + { + "filename" : "Reel4.MP4", + "idiom" : "universal" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/Reel4.dataset/Reel4.MP4 b/Rethread/Rethread/Assets.xcassets/Reel4.dataset/Reel4.MP4 new file mode 100644 index 0000000..153e469 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/Reel4.dataset/Reel4.MP4 differ diff --git a/Rethread/Rethread/Assets.xcassets/Reel5.dataset/Contents.json b/Rethread/Rethread/Assets.xcassets/Reel5.dataset/Contents.json new file mode 100644 index 0000000..952e8f6 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/Reel5.dataset/Contents.json @@ -0,0 +1,12 @@ +{ + "data" : [ + { + "filename" : "Reel5.MP4", + "idiom" : "universal" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/Reel5.dataset/Reel5.MP4 b/Rethread/Rethread/Assets.xcassets/Reel5.dataset/Reel5.MP4 new file mode 100644 index 0000000..81ab42c Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/Reel5.dataset/Reel5.MP4 differ diff --git a/Rethread/Rethread/Assets.xcassets/accessoryCover.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/accessoryCover.imageset/Contents.json new file mode 100644 index 0000000..c620c42 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/accessoryCover.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "accessoryCover.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/accessoryCover.imageset/accessoryCover.png b/Rethread/Rethread/Assets.xcassets/accessoryCover.imageset/accessoryCover.png new file mode 100644 index 0000000..ca067a2 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/accessoryCover.imageset/accessoryCover.png differ diff --git a/Rethread/Rethread/Assets.xcassets/arcHeader.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/arcHeader.imageset/Contents.json new file mode 100644 index 0000000..8f2bc6c --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/arcHeader.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "arcHeader.jpg", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/arcHeader.imageset/arcHeader.jpg b/Rethread/Rethread/Assets.xcassets/arcHeader.imageset/arcHeader.jpg new file mode 100644 index 0000000..1f51752 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/arcHeader.imageset/arcHeader.jpg differ diff --git a/Rethread/Rethread/Assets.xcassets/arcLetters.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/arcLetters.imageset/Contents.json new file mode 100644 index 0000000..fabb612 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/arcLetters.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "arcLetters.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/arcLetters.imageset/arcLetters.png b/Rethread/Rethread/Assets.xcassets/arcLetters.imageset/arcLetters.png new file mode 100644 index 0000000..d765a71 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/arcLetters.imageset/arcLetters.png differ diff --git a/Rethread/Rethread/Assets.xcassets/arcPants.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/arcPants.imageset/Contents.json new file mode 100644 index 0000000..717b5f5 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/arcPants.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "arcPants.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/arcPants.imageset/arcPants.png b/Rethread/Rethread/Assets.xcassets/arcPants.imageset/arcPants.png new file mode 100644 index 0000000..1b36be5 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/arcPants.imageset/arcPants.png differ diff --git a/Rethread/Rethread/Assets.xcassets/arcShirt.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/arcShirt.imageset/Contents.json new file mode 100644 index 0000000..b7bedc2 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/arcShirt.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "arcShirt.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/arcShirt.imageset/arcShirt.png b/Rethread/Rethread/Assets.xcassets/arcShirt.imageset/arcShirt.png new file mode 100644 index 0000000..8a6f70c Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/arcShirt.imageset/arcShirt.png differ diff --git a/Rethread/Rethread/Assets.xcassets/arc_1.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/arc_1.imageset/Contents.json new file mode 100644 index 0000000..570159e --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/arc_1.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "arc_1.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/arc_1.imageset/arc_1.png b/Rethread/Rethread/Assets.xcassets/arc_1.imageset/arc_1.png new file mode 100644 index 0000000..ac81edc Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/arc_1.imageset/arc_1.png differ diff --git a/Rethread/Rethread/Assets.xcassets/arc_2.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/arc_2.imageset/Contents.json new file mode 100644 index 0000000..c739af1 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/arc_2.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "arc_2.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/arc_2.imageset/arc_2.png b/Rethread/Rethread/Assets.xcassets/arc_2.imageset/arc_2.png new file mode 100644 index 0000000..435afdf Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/arc_2.imageset/arc_2.png differ diff --git a/Rethread/Rethread/Assets.xcassets/arc_3.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/arc_3.imageset/Contents.json new file mode 100644 index 0000000..4154c8f --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/arc_3.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "arc_3.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/arc_3.imageset/arc_3.png b/Rethread/Rethread/Assets.xcassets/arc_3.imageset/arc_3.png new file mode 100644 index 0000000..c352959 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/arc_3.imageset/arc_3.png differ diff --git a/Rethread/Rethread/Assets.xcassets/arc_4.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/arc_4.imageset/Contents.json new file mode 100644 index 0000000..45272b6 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/arc_4.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "arc_4.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/arc_4.imageset/arc_4.png b/Rethread/Rethread/Assets.xcassets/arc_4.imageset/arc_4.png new file mode 100644 index 0000000..961c614 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/arc_4.imageset/arc_4.png differ diff --git a/Rethread/Rethread/Assets.xcassets/arc_5.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/arc_5.imageset/Contents.json new file mode 100644 index 0000000..3afaa37 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/arc_5.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "arc_5.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/arc_5.imageset/arc_5.png b/Rethread/Rethread/Assets.xcassets/arc_5.imageset/arc_5.png new file mode 100644 index 0000000..646e18c Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/arc_5.imageset/arc_5.png differ diff --git a/Rethread/Rethread/Assets.xcassets/bottomsCover.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/bottomsCover.imageset/Contents.json new file mode 100644 index 0000000..fbf5938 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/bottomsCover.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "bottomsCover.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/bottomsCover.imageset/bottomsCover.png b/Rethread/Rethread/Assets.xcassets/bottomsCover.imageset/bottomsCover.png new file mode 100644 index 0000000..23a43ed Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/bottomsCover.imageset/bottomsCover.png differ diff --git a/Rethread/Rethread/Assets.xcassets/brokenplanet.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/brokenplanet.imageset/Contents.json new file mode 100644 index 0000000..f71420d --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/brokenplanet.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "brokenplanet.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/brokenplanet.imageset/brokenplanet.png b/Rethread/Rethread/Assets.xcassets/brokenplanet.imageset/brokenplanet.png new file mode 100644 index 0000000..1889ae4 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/brokenplanet.imageset/brokenplanet.png differ diff --git a/Rethread/Rethread/Assets.xcassets/cotoTaxi.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/cotoTaxi.imageset/Contents.json new file mode 100644 index 0000000..3f4c113 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/cotoTaxi.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "cotoTaxi.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/cotoTaxi.imageset/cotoTaxi.png b/Rethread/Rethread/Assets.xcassets/cotoTaxi.imageset/cotoTaxi.png new file mode 100644 index 0000000..dc58c33 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/cotoTaxi.imageset/cotoTaxi.png differ diff --git a/Rethread/Rethread/Assets.xcassets/meow_1.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/meow_1.imageset/Contents.json new file mode 100644 index 0000000..3bd6ad9 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/meow_1.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "meow_1.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/meow_1.imageset/meow_1.png b/Rethread/Rethread/Assets.xcassets/meow_1.imageset/meow_1.png new file mode 100644 index 0000000..efc5452 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/meow_1.imageset/meow_1.png differ diff --git a/Rethread/Rethread/Assets.xcassets/meow_2.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/meow_2.imageset/Contents.json new file mode 100644 index 0000000..7fa020a --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/meow_2.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "meow_2.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/meow_2.imageset/meow_2.png b/Rethread/Rethread/Assets.xcassets/meow_2.imageset/meow_2.png new file mode 100644 index 0000000..5f3d6e5 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/meow_2.imageset/meow_2.png differ diff --git a/Rethread/Rethread/Assets.xcassets/meow_3.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/meow_3.imageset/Contents.json new file mode 100644 index 0000000..2a7ad21 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/meow_3.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "meow_3.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/meow_3.imageset/meow_3.png b/Rethread/Rethread/Assets.xcassets/meow_3.imageset/meow_3.png new file mode 100644 index 0000000..1d6ee38 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/meow_3.imageset/meow_3.png differ diff --git a/Rethread/Rethread/Assets.xcassets/meow_4.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/meow_4.imageset/Contents.json new file mode 100644 index 0000000..bd6f88f --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/meow_4.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "meow_4.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/meow_4.imageset/meow_4.png b/Rethread/Rethread/Assets.xcassets/meow_4.imageset/meow_4.png new file mode 100644 index 0000000..bf3681b Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/meow_4.imageset/meow_4.png differ diff --git a/Rethread/Rethread/Assets.xcassets/patagoniaFont.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/patagoniaFont.imageset/Contents.json new file mode 100644 index 0000000..24f2da4 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/patagoniaFont.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "patagoniaFont.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/patagoniaFont.imageset/patagoniaFont.png b/Rethread/Rethread/Assets.xcassets/patagoniaFont.imageset/patagoniaFont.png new file mode 100644 index 0000000..ced0b30 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/patagoniaFont.imageset/patagoniaFont.png differ diff --git a/Rethread/Rethread/Assets.xcassets/patagoniaHeader.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/patagoniaHeader.imageset/Contents.json new file mode 100644 index 0000000..e7038a5 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/patagoniaHeader.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "patagoniaHeader.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/patagoniaHeader.imageset/patagoniaHeader.png b/Rethread/Rethread/Assets.xcassets/patagoniaHeader.imageset/patagoniaHeader.png new file mode 100644 index 0000000..a34ebfa Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/patagoniaHeader.imageset/patagoniaHeader.png differ diff --git a/Rethread/Rethread/Assets.xcassets/patagoniaQuar.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/patagoniaQuar.imageset/Contents.json new file mode 100644 index 0000000..df1db54 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/patagoniaQuar.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "patagoniaQuar.jpg", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/patagoniaQuar.imageset/patagoniaQuar.jpg b/Rethread/Rethread/Assets.xcassets/patagoniaQuar.imageset/patagoniaQuar.jpg new file mode 100644 index 0000000..4990dc4 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/patagoniaQuar.imageset/patagoniaQuar.jpg differ diff --git a/Rethread/Rethread/Assets.xcassets/shoesHeader.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/shoesHeader.imageset/Contents.json new file mode 100644 index 0000000..389fe56 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/shoesHeader.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "shoesHeader.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/shoesHeader.imageset/shoesHeader.png b/Rethread/Rethread/Assets.xcassets/shoesHeader.imageset/shoesHeader.png new file mode 100644 index 0000000..3b7e2b4 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/shoesHeader.imageset/shoesHeader.png differ diff --git a/Rethread/Rethread/Assets.xcassets/sus1.dataset/Contents.json b/Rethread/Rethread/Assets.xcassets/sus1.dataset/Contents.json new file mode 100644 index 0000000..a98bbc8 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/sus1.dataset/Contents.json @@ -0,0 +1,12 @@ +{ + "data" : [ + { + "filename" : "sus1.MP4", + "idiom" : "universal" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/sus1.dataset/sus1.mp4 b/Rethread/Rethread/Assets.xcassets/sus1.dataset/sus1.mp4 new file mode 100644 index 0000000..c21d98d Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/sus1.dataset/sus1.mp4 differ diff --git a/Rethread/Rethread/Assets.xcassets/sus2.dataset/Contents.json b/Rethread/Rethread/Assets.xcassets/sus2.dataset/Contents.json new file mode 100644 index 0000000..dd4b05d --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/sus2.dataset/Contents.json @@ -0,0 +1,12 @@ +{ + "data" : [ + { + "filename" : "sus2.mp4", + "idiom" : "universal" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/sus2.dataset/sus2.mp4 b/Rethread/Rethread/Assets.xcassets/sus2.dataset/sus2.mp4 new file mode 100644 index 0000000..9538db4 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/sus2.dataset/sus2.mp4 differ diff --git a/Rethread/Rethread/Assets.xcassets/sus3.dataset/Contents.json b/Rethread/Rethread/Assets.xcassets/sus3.dataset/Contents.json new file mode 100644 index 0000000..aaa99ce --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/sus3.dataset/Contents.json @@ -0,0 +1,12 @@ +{ + "data" : [ + { + "filename" : "sus3.mp4", + "idiom" : "universal" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/sus3.dataset/sus3.mp4 b/Rethread/Rethread/Assets.xcassets/sus3.dataset/sus3.mp4 new file mode 100644 index 0000000..db3ae84 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/sus3.dataset/sus3.mp4 differ diff --git a/Rethread/Rethread/Assets.xcassets/sweatShirt 1.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/sweatShirt 1.imageset/Contents.json new file mode 100644 index 0000000..594d773 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/sweatShirt 1.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "sweatshirt.jpeg", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/sweatShirt 1.imageset/sweatshirt.jpeg b/Rethread/Rethread/Assets.xcassets/sweatShirt 1.imageset/sweatshirt.jpeg new file mode 100644 index 0000000..befdd4f Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/sweatShirt 1.imageset/sweatshirt.jpeg differ diff --git a/Rethread/Rethread/Assets.xcassets/tshirtCover.imageset/Contents.json b/Rethread/Rethread/Assets.xcassets/tshirtCover.imageset/Contents.json new file mode 100644 index 0000000..dd891e3 --- /dev/null +++ b/Rethread/Rethread/Assets.xcassets/tshirtCover.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "tshirtCover.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/Rethread/Rethread/Assets.xcassets/tshirtCover.imageset/tshirtCover.png b/Rethread/Rethread/Assets.xcassets/tshirtCover.imageset/tshirtCover.png new file mode 100644 index 0000000..5ad0f10 Binary files /dev/null and b/Rethread/Rethread/Assets.xcassets/tshirtCover.imageset/tshirtCover.png differ diff --git a/Rethread/Rethread/Core/ContentView.swift b/Rethread/Rethread/Core/ContentView.swift index f15249f..da6230f 100644 --- a/Rethread/Rethread/Core/ContentView.swift +++ b/Rethread/Rethread/Core/ContentView.swift @@ -5,18 +5,14 @@ struct ContentView: View { var body: some View { - Group { - if viewModel.isLoading { - ProgressView("Loading...") - } else { - if viewModel.currentUser?.onboardingComplete == false { - WelcomeView() - } else if viewModel.userSession != nil { - HomeView() - } else { - MainView() - } - } + if viewModel.isLoading { + ProgressView("Loading...") + } else if viewModel.currentUser?.onboardingComplete == false { + WelcomeView() + } else if viewModel.userSession != nil { + MainView().environmentObject(self.viewModel) + } else { + AuthenticationView() } } } diff --git a/Rethread/Rethread/Core/OnboardingApp.swift b/Rethread/Rethread/Core/OnboardingApp.swift index 366e95a..cad6c45 100644 --- a/Rethread/Rethread/Core/OnboardingApp.swift +++ b/Rethread/Rethread/Core/OnboardingApp.swift @@ -3,18 +3,47 @@ import SwiftUI import Firebase +class AppDelegate: NSObject, UIApplicationDelegate { + func application(_ application: UIApplication, + didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey : Any]? = nil) -> Bool { + FirebaseApp.configure() + print("SwiftUI_2_Lifecycle_PhoneNumber_AuthApp application is starting up. ApplicationDelegate didFinishLaunchingWithOptions.") + return true + } + + func application(_ application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: Data) { + print("\(#function)") + Auth.auth().setAPNSToken(deviceToken, type: .sandbox) + } + + func application(_ application: UIApplication, didReceiveRemoteNotification notification: [AnyHashable : Any], fetchCompletionHandler completionHandler: @escaping (UIBackgroundFetchResult) -> Void) { + print("\(#function)") + if Auth.auth().canHandleNotification(notification) { + completionHandler(.noData) + return + } + } + + func application(_ application: UIApplication, open url: URL, options: [UIApplication.OpenURLOptionsKey : Any]) -> Bool { + print("\(#function)") + if Auth.auth().canHandle(url) { + return true + } + return false + } +} + + @main struct OnboardingApp: App { + @UIApplicationDelegateAdaptor(AppDelegate.self) var delegate @StateObject var viewModel = AuthViewModel() - init() { - FirebaseApp.configure() - } - var body: some Scene { WindowGroup { ContentView() .environmentObject(viewModel) +// MainView().environmentObject(viewModel) } } } diff --git a/Rethread/Rethread/GoogleService-Info.plist b/Rethread/Rethread/GoogleService-Info.plist new file mode 100644 index 0000000..1a525b9 --- /dev/null +++ b/Rethread/Rethread/GoogleService-Info.plist @@ -0,0 +1,34 @@ + + + + + CLIENT_ID + 69711373157-t12e6rrs7ojav6hmg4r8avdvt2tmf5s3.apps.googleusercontent.com + REVERSED_CLIENT_ID + com.googleusercontent.apps.69711373157-t12e6rrs7ojav6hmg4r8avdvt2tmf5s3 + API_KEY + AIzaSyCt95kuSORiMMuxgV7BXBI0LqhQ78E3CS0 + GCM_SENDER_ID + 69711373157 + PLIST_VERSION + 1 + BUNDLE_ID + com.techstart.rethread + PROJECT_ID + rethread-6c539 + STORAGE_BUCKET + rethread-6c539.appspot.com + IS_ADS_ENABLED + + IS_ANALYTICS_ENABLED + + IS_APPINVITE_ENABLED + + IS_GCM_ENABLED + + IS_SIGNIN_ENABLED + + GOOGLE_APP_ID + 1:69711373157:ios:b81d19d8aca6a16f4ef78c + + \ No newline at end of file diff --git a/Rethread/Rethread/Info.plist b/Rethread/Rethread/Info.plist index 83fb1ab..74835fe 100644 --- a/Rethread/Rethread/Info.plist +++ b/Rethread/Rethread/Info.plist @@ -2,6 +2,8 @@ + FirebaseAppDelegateProxyEnabled + CFBundleURLTypes @@ -9,9 +11,14 @@ Editor CFBundleURLSchemes - com.googleusercontent.apps.69711373157-smt51cs82nik0nceo6slguta9vmaip00 + app-1-69711373157-ios-b81d19d8aca6a16f4ef78c + com.googleusercontent.apps.69711373157-t12e6rrs7ojav6hmg4r8avdvt2tmf5s3 + UIBackgroundModes + + remote-notification + diff --git a/Rethread/Rethread/Models/FilterModel.swift b/Rethread/Rethread/Models/FilterModel.swift new file mode 100644 index 0000000..5b9c4c0 --- /dev/null +++ b/Rethread/Rethread/Models/FilterModel.swift @@ -0,0 +1,49 @@ +// FilterModel.swift + +import Foundation + +struct ClothingItem: Identifiable { + let id = UUID() + var name: String + var type: ClothingType + var color: String + var price: Int + var imageName: String + var style: ClothingStyle +} + +enum ClothingType: String, CaseIterable { + case pants = "Pants" + case tShirt = "T-Shirt" + case jacket = "Jacket" + +} + +enum ClothingStyle: String, CaseIterable { + case active = "Active" + case classic = "Classic" + case casual = "Casual" +} + +var allItems: [ClothingItem] = [ + // Populate with your actual clothing items + ClothingItem(name: "1/4 zip fleece", type: .jacket, color: "Red", price: Int(100), imageName: "patagoniaQuar", style: .active), + // Add more items... +] + + +var ArcteryxItems: [ClothingItem] = [ + // Populate with your actual clothing items + ClothingItem(name: "Beta Jacket".uppercased(), type: .jacket, color: "Red", price: Int(500), imageName: "BETAJACKETMENS", style: .active), + ClothingItem(name: "Trevon Pants".uppercased(), type: .pants, color: "Red", price: Int(160), imageName: "arcPants", style: .classic), + ClothingItem(name: "Ionia Logo Shirt SS".uppercased(), type: .tShirt, color: "Red", price: Int(80), imageName: "arcShirt", style: .casual), + ClothingItem(name: "BETA AR JACKET", type: .jacket, color: "Blue", price: Int(170), imageName: "arc_1", style: .casual), + ClothingItem(name: "BETA AR JACKET ", type: .jacket, color: "Red", price: Int(750), imageName: "arc_3", style: .active), + ClothingItem(name: "SABRE INSULATED JACKET", type: .jacket, color: "Blue", price: Int(1000), imageName: "arc_1", style: .classic), + ClothingItem(name: "CORMAC POLO SHIRT", type: .tShirt, color: "Blue", price: Int(140), imageName: "arc_4", style: .active), + ClothingItem(name: "KYANITE LW JACKET", type: .jacket, color: "Blue", price: Int(170), imageName: "arc_5", style: .active), + ClothingItem(name: "BETA AR JACKET ", type: .jacket, color: "Red", price: Int(750), imageName: "arc_1", style: .active), + + + +] diff --git a/Rethread/Rethread/Models/MapViewModel.swift b/Rethread/Rethread/Models/MapViewModel.swift index 7526762..071c1b9 100644 --- a/Rethread/Rethread/Models/MapViewModel.swift +++ b/Rethread/Rethread/Models/MapViewModel.swift @@ -2,28 +2,19 @@ import MapKit - final class MapViewModel: NSObject, ObservableObject, CLLocationManagerDelegate { - @Published var region = MKCoordinateRegion(center: CLLocationCoordinate2D(latitude: 37.331516, longitude: -121.891054), span: MKCoordinateSpan(latitudeDelta: 0.05, longitudeDelta: 0.05)) - - - var locationManager: CLLocationManager? - - func isUserLocationOn() { - if CLLocationManager.locationServicesEnabled() { - locationManager = CLLocationManager() - locationManager!.delegate = self - } - else { - print("Show an alert showing user that they need to turn on location") - } + override init() { + locationManager = CLLocationManager() + super.init() + locationManager.delegate = self } - private func checkLocationAuthorization () { - guard let locationManager = locationManager else { return } + @Published var region = MKCoordinateRegion(center: CLLocationCoordinate2D(latitude: 37.331516, longitude: -121.891054), span: MKCoordinateSpan(latitudeDelta: 0.05, longitudeDelta: 0.05)) + let locationManager: CLLocationManager + private func checkLocationAuthorization () { switch locationManager.authorizationStatus { case .notDetermined: diff --git a/Rethread/Rethread/Models/MediaModel.swift b/Rethread/Rethread/Models/MediaModel.swift new file mode 100644 index 0000000..3028f9c --- /dev/null +++ b/Rethread/Rethread/Models/MediaModel.swift @@ -0,0 +1,33 @@ +// +// MediaModel.swift +// InstReels +// +// + +import Foundation + +struct Media: Identifiable { + var id = UUID().uuidString + var url: String + var title: String + var isExpanded = false + var vidType: VideoType +} + +enum VideoType: String, CaseIterable { + case all = "All" + case active = "Active" + case classic = "Classic" + case casual = "Casual" +} + +extension Media { + static var previews: [Self] { + [ + Media(url: "https://www.youtube.com/shorts/1mhqy38JeN4", title: "I love Sustainable fashion", vidType: .casual), + Media(url: "Reel3", title: "ReThread rocks!", vidType: .classic), + Media(url: "Reel4", title: "How to buy sustainable fashaion", vidType: .active), + Media(url: "Reel5", title: "Become a programmer without a degree", vidType: .active) + ] + } +} diff --git a/Rethread/Rethread/Models/PhotoPickerModel.swift b/Rethread/Rethread/Models/PhotoPickerModel.swift new file mode 100644 index 0000000..0465950 --- /dev/null +++ b/Rethread/Rethread/Models/PhotoPickerModel.swift @@ -0,0 +1,41 @@ +// PhotoPickerModel.swift +import SwiftUI +import Foundation +import PhotosUI + +struct accessCameraView: UIViewControllerRepresentable { + + @Binding var selectedImage: UIImage? + @Environment(\.presentationMode) var isPresented + + func makeUIViewController(context: Context) -> UIImagePickerController { + let imagePicker = UIImagePickerController() + imagePicker.sourceType = .camera + imagePicker.allowsEditing = true + imagePicker.delegate = context.coordinator + return imagePicker + } + + func updateUIViewController(_ uiViewController: UIImagePickerController, context: Context) { + + } + + func makeCoordinator() -> Coordinator { + return Coordinator(picker: self) + } +} + +// Coordinator will help to preview the selected image in the View. +class Coordinator: NSObject, UINavigationControllerDelegate, UIImagePickerControllerDelegate { + var picker: accessCameraView + + init(picker: accessCameraView) { + self.picker = picker + } + + func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) { + guard let selectedImage = info[.originalImage] as? UIImage else { return } + self.picker.selectedImage = selectedImage + self.picker.isPresented.wrappedValue.dismiss() + } +} diff --git a/Rethread/Rethread/Models/ReelModel.swift b/Rethread/Rethread/Models/ReelModel.swift new file mode 100644 index 0000000..5e1611e --- /dev/null +++ b/Rethread/Rethread/Models/ReelModel.swift @@ -0,0 +1,14 @@ +// +// ReelModel.swift +// InstReels +// +// + +import SwiftUI +import AVKit + +struct Reel: Identifiable { + var id = UUID() + var player: AVPlayer + var mediaFile: Media +} diff --git a/Rethread/Rethread/Reel2.mov b/Rethread/Rethread/Reel2.mov new file mode 100644 index 0000000..55dac15 Binary files /dev/null and b/Rethread/Rethread/Reel2.mov differ diff --git a/Rethread/Rethread/Reel3.MP4 b/Rethread/Rethread/Reel3.MP4 new file mode 100644 index 0000000..c906218 Binary files /dev/null and b/Rethread/Rethread/Reel3.MP4 differ diff --git a/Rethread/Rethread/Reel4.MP4 b/Rethread/Rethread/Reel4.MP4 new file mode 100644 index 0000000..153e469 Binary files /dev/null and b/Rethread/Rethread/Reel4.MP4 differ diff --git a/Rethread/Rethread/Reel5.MP4 b/Rethread/Rethread/Reel5.MP4 new file mode 100644 index 0000000..81ab42c Binary files /dev/null and b/Rethread/Rethread/Reel5.MP4 differ diff --git a/Rethread/Rethread/Rethread.entitlements b/Rethread/Rethread/Rethread.entitlements new file mode 100644 index 0000000..903def2 --- /dev/null +++ b/Rethread/Rethread/Rethread.entitlements @@ -0,0 +1,8 @@ + + + + + aps-environment + development + + diff --git a/Rethread/Rethread/UserAuthentication/AuthViewModel.swift b/Rethread/Rethread/UserAuthentication/AuthViewModel.swift index ebe927c..282b801 100644 --- a/Rethread/Rethread/UserAuthentication/AuthViewModel.swift +++ b/Rethread/Rethread/UserAuthentication/AuthViewModel.swift @@ -7,10 +7,12 @@ import FirebaseFirestoreSwift @MainActor class AuthViewModel: ObservableObject { @Published var userSession: FirebaseAuth.User? + @Published var tempSession: FirebaseAuth.User? @Published var currentUser: User? @Published var CLIENT_CODE: String = "" private var verificationId: String? @Published var isLoading: Bool = true + @Published var isVerified: Bool = false init(){ self.userSession = Auth.auth().currentUser @@ -75,36 +77,69 @@ class AuthViewModel: ObservableObject { func deleteAccount() { //TODO: Implement user deleting account. } + + // Send Verification Code + func sendVerificationCode(phoneNumber: String, completion: @escaping (Bool, Error?) -> Void) { + PhoneAuthProvider.provider().verifyPhoneNumber(phoneNumber, uiDelegate: nil) { verificationID, error in + if let error = error { + print("Error sending verification code: \(error.localizedDescription)") + completion(false, error) + return + } + guard let verificationID = verificationID else { + print("Verification ID not received") + completion(false, nil) + return + } + self.verificationId = verificationID + completion(true, nil) + } + } + // Attempt to sign in and retrieve phone number without fully establishing a session + func signInAndRetrievePhoneNumber(withEmail email: String, password: String, completion: @escaping (String?, Error?) -> Void) async { + do { + // Sign in the user + let authResult = try await Auth.auth().signIn(withEmail: email, password: password) + + // Fetch user details from Firestore + let uid = authResult.user.uid + let userDocument = try await Firestore.firestore().collection("users").document(uid).getDocument() + + if let userDocument = userDocument.data(), let phoneNumber = userDocument["phoneNumber"] as? String { + // Successfully retrieved phone number + + // Sign out the user + try Auth.auth().signOut() + + // Return the phone number + completion(phoneNumber, nil) + } else { + // Phone number not found in the document + completion(nil, NSError(domain: "AppError", code: 0, userInfo: [NSLocalizedDescriptionKey: "Phone number not found in Firestore."])) + } + } catch { + completion(nil, error) + } + } + + + + // Verify Phone Number + func verifyPhoneNumber(verificationCode: String) async throws { + guard let verificationId = self.verificationId else { + throw NSError(domain: "AppError", code: 0, userInfo: [NSLocalizedDescriptionKey: "Verification ID not found"]) + } + + let credential = PhoneAuthProvider.provider().credential(withVerificationID: verificationId, verificationCode: verificationCode) + _ = try await Auth.auth().signIn(with: credential) + } + + // Fetch User func fetchUser() async { guard let uid = Auth.auth().currentUser?.uid else {return} guard let snapshot = try? await Firestore.firestore().collection("users").document(uid).getDocument() else {return} self.currentUser = try? snapshot.data(as: User.self) } - - - -// func sendPhoneAuth() async { -// PhoneAuthProvider.provider().verifyPhoneNumber("+16505551111", uiDelegate: nil) { [weak self] verificationID, error in -// guard let verificationID = verificationID, error == nil else { -// print("DEBUG: Error sending phone auth: \(error!.localizedDescription)") -// return -// } -// self?.verificationId = verificationID -// } -// } -// func verifyPhoneAuth(otp: String) async { -// guard let verificationId = self.verificationId else {return} -// let credential = PhoneAuthProvider.provider().credential(withVerificationID: verificationId, verificationCode: otp) -// -// Auth.auth().signIn(with: credential) { (result, error) in -// if let error = error { -// print("DEBUG: Error verifying phone auth: \(error.localizedDescription)") -// return -// } -// self.userSession = result?.user -// } -// } - } diff --git a/Rethread/Rethread/Views/AccountNotificationView.swift b/Rethread/Rethread/Views/AccountNotificationView.swift new file mode 100644 index 0000000..74fdb1b --- /dev/null +++ b/Rethread/Rethread/Views/AccountNotificationView.swift @@ -0,0 +1,42 @@ +// AccountNotificationView.swift + +import SwiftUI + +struct AccountNotificationView: View { + var body: some View { + + VStack(alignment: .leading) { + NotificationComponent(title: "Application Notifications", content: "Click to enable push notifications sent by reThread") + + NotificationComponent(title: "Email Notification", content: "Click to be notified of updates and promotions through your email") + Spacer() + } + .padding(.vertical,100) + } +} + +#Preview { + AccountNotificationView() +} + +struct NotificationComponent: View { + var title: String + var content: String + @State private var isOn = true + + + var body: some View { + Text(title) + .fontWeight(.bold) + .padding(.horizontal) + HStack { + Toggle(isOn: $isOn, label: { + Text(content) + }) + .tint(.blue) + .padding(.horizontal) + .padding(.bottom, 32) + + } + } +} diff --git a/Rethread/Rethread/Views/AccountSettingsView.swift b/Rethread/Rethread/Views/AccountSettingsView.swift new file mode 100644 index 0000000..f84a5e0 --- /dev/null +++ b/Rethread/Rethread/Views/AccountSettingsView.swift @@ -0,0 +1,13 @@ +// AccountSettingsView.swift + +import SwiftUI + +struct AccountSettingsView: View { + var body: some View { + Text("Hello, World!") + } +} + +#Preview { + AccountSettingsView() +} diff --git a/Rethread/Rethread/Views/AuthenticationView.swift b/Rethread/Rethread/Views/AuthenticationView.swift new file mode 100644 index 0000000..2db5aa1 --- /dev/null +++ b/Rethread/Rethread/Views/AuthenticationView.swift @@ -0,0 +1,105 @@ +import SwiftUI +import NavigationTransitions + +#if canImport(UIKit) +extension View { + func hideKeyboard() { + UIApplication.shared.sendAction(#selector(UIResponder.resignFirstResponder), to: nil, from: nil, for: nil) + } +} +#endif + +struct AuthenticationView: View { + @State private var path: [String] = [] + + var body: some View { + NavigationStack (path: $path) { + ZStack (alignment: .bottom) { + // Add Image + Image("flowerMainPage") + .resizable() + .overlay(Color.black.opacity(0.1)) + .clipped() + .edgesIgnoringSafeArea(.all) + .padding(.bottom, 220) + + // Botom Part + VStack (spacing: 50) { + + HStack { + Text("Get involved with" + "\n" + "sustainable fashion") + .font(.system(size: 20)) + .fontWeight(.semibold) + .foregroundColor(Color.primaryDark) + .opacity(0.5) + .multilineTextAlignment(.leading) + .lineSpacing(6) + Spacer() + } + .padding(.horizontal, 35) + .padding(.top, 25) + + + + VStack (spacing: 17) { + Button(action: { + path.append("SignInView") + }) { + HStack { + Text("Log In") + } + .frame(maxWidth: .infinity, maxHeight: .infinity) + } + .buttonStyle(PrimaryButtonStyle(width: 300)) + + HStack { + Spacer() + + Button(action: { + path.append("SignUpView") + }) { + Text("Create Account") + .foregroundColor(Color.primaryDark) + .fontWeight(.semibold) + .underline() + } + } + .padding(.horizontal, 35) + } + .navigationDestination(for: String.self) { view in + if view == "SignInView" { + SignInView(path: $path) + } else if view == "SignUpView" { + SignUpView(path: $path) + } else if view == "WelcomeView" { + WelcomeView() + } + } + } + .background(RoundedCorners( + color: .white, + tl: 20, + tr: 20 + )) + .frame(height: 270) + } + .frame(maxHeight: .infinity) + } + .navigationTransition(.slide(axis: .vertical)) + // Safe area for iPhone X and above + .edgesIgnoringSafeArea(.all) // This will extend the content to the edges + .background(Color(UIColor.systemGray6)) + .overlay( + GeometryReader { geometry in + Color.white.opacity(0.3) // Adjust the opacity here for semi-transparency + .frame(width: geometry.size.width, height: geometry.safeAreaInsets.top) + .edgesIgnoringSafeArea(.top) + }, alignment: .top + ) + } +} + +#Preview { + AuthenticationView() +} + diff --git a/Rethread/Rethread/Views/ClothingItemView.swift b/Rethread/Rethread/Views/ClothingItemView.swift deleted file mode 100644 index 4e885d4..0000000 --- a/Rethread/Rethread/Views/ClothingItemView.swift +++ /dev/null @@ -1,122 +0,0 @@ -// ClothingItemView.swift - -import SwiftUI - -struct ClothingItemView: View { - let columns: [GridItem] = [ - GridItem(.flexible()), - GridItem(.flexible()), - ] - - @State private var isHidden = false - - - var body: some View { - - VStack { - VStack { - HomeBarView() - MainSearchBar() - - ScrollView(.horizontal, showsIndicators: false) { - HStack { - Button(action: { - withAnimation { - isHidden.toggle() - } - }, label: { - Text("Category") - Image(systemName: "chevron.down") - }) - .buttonStyle(.borderedProminent) - .tint(.white) - .foregroundStyle(Color(hex: "#2C4C52")) - .overlay( - RoundedRectangle(cornerSize: CGSize(width: 5, height: 5)) - .stroke(Color(hex: "#2C4C52")) - ) - - - - Button(action: { - }, label: { - Text("Color") - Image(systemName: "chevron.down") - }) - .buttonStyle(.borderedProminent) - .tint(.white) - .foregroundStyle(Color(hex: "#2C4C52")) - .overlay( - RoundedRectangle(cornerSize: CGSize(width: 5, height: 5)) - .stroke(Color(hex: "#2C4C52")) - ) - - - Button(action: {}, label: { - Text("Gender") - Image(systemName: "chevron.down") - - }) - .buttonStyle(.borderedProminent) - .tint(.white) - .foregroundStyle(Color(hex: "#2C4C52")) - .overlay( - RoundedRectangle(cornerSize: CGSize(width: 5, height: 5)) - .stroke(Color(hex: "#2C4C52")) - ) - - } - } - .padding(.horizontal) - } - - ZStack(alignment: .leading) { - VStack { - VStack() { - Text("PLACEHOLDER") - .padding() - Spacer() - - } - .frame(maxWidth: .infinity, maxHeight: .infinity) - .background(.white) - VStack { - Text("") - - } - .frame(maxWidth: .infinity, maxHeight: 300) - } - .frame(maxWidth: .infinity, maxHeight: .infinity) - .zIndex(5) - .opacity(isHidden ? 0 : 1) - .transition(.slide) - - - - - VStack { - HStack { - Text("Shirts") - .font(.title) - .fontWeight(.bold) - Spacer() - } - .padding(.horizontal) - - - LazyVGrid(columns: columns) { - ForEach(0..<3) {index in - ClothCard(width: 160, height: 150, clothingItem: Image("sweatshirt")) - } - } - .zIndex(-1) - Spacer() - } - } - } - } -} - -#Preview { - ClothingItemView() -} diff --git a/Rethread/Rethread/Views/FullVidView.swift b/Rethread/Rethread/Views/FullVidView.swift new file mode 100644 index 0000000..18487f2 --- /dev/null +++ b/Rethread/Rethread/Views/FullVidView.swift @@ -0,0 +1,82 @@ +// +// MainView.swift +// InstReels +// +// + +import SwiftUI + +struct FullVidView: View { + + init() { + UITabBar.appearance().isHidden = true + } + + @State var currentTab = "Reel" + + enum Tab: String, CaseIterable { + case search = "Search", reel = "Reel", home = "Home" + + var image: String { + switch self { + case .home: "house.fill" + case .search: "magnifyingglass" + case .reel: "play.rectangle" + } + } + } + + + var body: some View { + VStack(spacing: 0) { + TabView(selection: $currentTab) { + ForEach(Tab.allCases, id: \.self) { tab in + + if tab == .reel { + ReelView() + .tag(tab.rawValue) + } else { + Rectangle() + .fill(Color(uiColor: .systemGray6)) + .frame(width: 300, height: 500) + .clipShape(RoundedRectangle(cornerRadius: 12)) + .overlay { + Text(tab.rawValue) + } + .tag(tab.rawValue) + } + + } + + } + + HStack(spacing: 0) { + ForEach(Tab.allCases, id: \.self) { tab in + makeTabBarButton(for: tab) + } + } + } + } + +} + +extension FullVidView { + private func makeTabBarButton(for tab: Tab) -> some View { + Button { + withAnimation { currentTab = tab.rawValue } + } label: { + Image(systemName: tab.image) + .resizable() + .renderingMode(.template) + .foregroundStyle(.gray) + .aspectRatio(contentMode: .fit) + .frame(width: 26, height: 26) + .padding(.top, 16) + .frame(maxWidth: .infinity) + } + } +} + +#Preview { + FullVidView() +} \ No newline at end of file diff --git a/Rethread/Rethread/Views/GenAccessoriesView.swift b/Rethread/Rethread/Views/GenAccessoriesView.swift new file mode 100644 index 0000000..823f602 --- /dev/null +++ b/Rethread/Rethread/Views/GenAccessoriesView.swift @@ -0,0 +1,115 @@ +// GenAccessoriesView.swift + +import SwiftUI + +// aboutArc'teryxBrandView.swift + + +import SwiftUI + + + +struct GenAccessoriesView: View { + + + @State private var selectedType: ClothingType? = nil + @State private var selectedColor: String? = nil + @State private var maxPrice: Int = 500 + + let columns: [GridItem] = [ + GridItem(.flexible()), + GridItem(.flexible()), + ] + var filteredItems: [ClothingItem] { + ArcteryxItems.filter { item in + (selectedType == nil || item.type == selectedType) && + (selectedColor == nil || item.color == selectedColor) && + item.price <= maxPrice + } + } + + + var body: some View { + NavigationStack { + ScrollView(showsIndicators: false) { + VStack { + Image("accessoryCover") + .resizable() + .aspectRatio(contentMode: .fill) + } + Spacer() + + VStack(alignment: .leading) { + VStack { + Picker("Type", selection: $selectedType) { + Text("All").tag(ClothingType?.none) + ForEach(ClothingType.allCases, id: \.self) { type in + Text(type.rawValue).tag(type as ClothingType?) + } + } + .padding(.vertical) + .pickerStyle(.segmented) + + Picker("Style", selection: $selectedColor) { + Text("All").tag(String?.none) + .foregroundStyle(Color(hex: "#2C4C52")) + Text("Active").tag("Active" as String?) + Text("Classic").tag("Classic" as String?) + Text("Casual").tag("Casual" as String?) + Text("Blue").tag("Blue" as String?) + } + } + .padding(.vertical) + .foregroundStyle(Color(hex: "#2C4C52")) + + .pickerStyle(.segmented) + + HStack { + Text("$0") + Slider(value: Binding(get: { + Double(maxPrice) + }, set: { newValue in + maxPrice = Int(newValue) + }), in: 0...500, step: 50) // Only allow integer values + .tint(Color(hex: "#2C4C52")) + + Text("$\(maxPrice)") + } + .foregroundStyle(Color(hex: "#2C4C52")) + .padding(.horizontal) + } + .padding(.horizontal) + + HStack { + Text("Shop Accessories") + .font(.title2) + .fontWeight(.bold) + Spacer() + } + .padding() + + + + LazyVGrid(columns: columns) { + ForEach(filteredItems) { clothingItem in + NavigationLink(destination: ProductView(productImage: clothingItem.imageName, productName: clothingItem.name, productPrice: clothingItem.price).onAppear { + }.onDisappear { + }) { + ClothCard(width: 160, height: 150, clothingItem: clothingItem) + } + } + } + Spacer() + } + + } + + .tint(Color(hex: "#2C4C52")) + } + } + + + +#Preview { + GenAccessoriesView() +} diff --git a/Rethread/Rethread/Views/GenBottomsView.swift b/Rethread/Rethread/Views/GenBottomsView.swift new file mode 100644 index 0000000..53bed91 --- /dev/null +++ b/Rethread/Rethread/Views/GenBottomsView.swift @@ -0,0 +1,111 @@ + +import SwiftUI + + + +struct GenBottomsView: View { + + + @State private var selectedType: ClothingType? = nil + @State private var selectedColor: String? = nil + @State private var maxPrice: Int = 500 + + let columns: [GridItem] = [ + GridItem(.flexible()), + GridItem(.flexible()), + ] + var filteredItems: [ClothingItem] { + ArcteryxItems.filter { item in + (selectedType == nil || item.type == selectedType) && + (selectedColor == nil || item.color == selectedColor) && + item.price <= maxPrice + } + } + + + var body: some View { + NavigationStack { + ScrollView(showsIndicators: false) { + VStack { + Image("bottomsCover") + .resizable() + .aspectRatio(contentMode: .fill) + } + Spacer() + + VStack(alignment: .leading) { + VStack { + Picker("Type", selection: $selectedType) { + Text("All").tag(ClothingType?.none) + ForEach(ClothingType.allCases, id: \.self) { type in + Text(type.rawValue).tag(type as ClothingType?) + } + } + .padding(.vertical) + .pickerStyle(.segmented) + + Picker("Style", selection: $selectedColor) { + Text("All").tag(String?.none) + .foregroundStyle(Color(hex: "#2C4C52")) + Text("Active").tag("Active" as String?) + Text("Classic").tag("Classic" as String?) + Text("Casual").tag("Casual" as String?) + Text("Blue").tag("Blue" as String?) + } + } + .padding(.vertical) + .foregroundStyle(Color(hex: "#2C4C52")) + + .pickerStyle(.segmented) + + HStack { + Text("$0") + Slider(value: Binding(get: { + Double(maxPrice) + }, set: { newValue in + maxPrice = Int(newValue) + }), in: 0...500, step: 50) // Only allow integer values + .tint(Color(hex: "#2C4C52")) + + Text("$\(maxPrice)") + } + .foregroundStyle(Color(hex: "#2C4C52")) + .padding(.horizontal) + } + .padding(.horizontal) + + HStack { + Text("Shop Bottoms") + .font(.title2) + .fontWeight(.bold) + Spacer() + } + .padding() + + + + LazyVGrid(columns: columns) { + ForEach(filteredItems) { clothingItem in + NavigationLink(destination: ProductView(productImage: clothingItem.imageName, productName: clothingItem.name, productPrice: clothingItem.price).onAppear { + }.onDisappear { + }) { + ClothCard(width: 160, height: 150, clothingItem: clothingItem) + } + } + } + Spacer() + } + + } + + .tint(Color(hex: "#2C4C52")) + } + } + + + +#Preview { + GenBottomsView() +} + + diff --git a/Rethread/Rethread/Views/GenShoesView.swift b/Rethread/Rethread/Views/GenShoesView.swift new file mode 100644 index 0000000..da05e44 --- /dev/null +++ b/Rethread/Rethread/Views/GenShoesView.swift @@ -0,0 +1,111 @@ + +import SwiftUI + + + +struct GenShoesView: View { + + + @State private var selectedType: ClothingType? = nil + @State private var selectedColor: String? = nil + @State private var maxPrice: Int = 500 + + let columns: [GridItem] = [ + GridItem(.flexible()), + GridItem(.flexible()), + ] + var filteredItems: [ClothingItem] { + ArcteryxItems.filter { item in + (selectedType == nil || item.type == selectedType) && + (selectedColor == nil || item.color == selectedColor) && + item.price <= maxPrice + } + } + + + var body: some View { + NavigationStack { + ScrollView(showsIndicators: false) { + VStack { + Image("shoesHeader") + .resizable() + .aspectRatio(contentMode: .fill) + } + Spacer() + + VStack(alignment: .leading) { + VStack { + Picker("Type", selection: $selectedType) { + Text("All").tag(ClothingType?.none) + ForEach(ClothingType.allCases, id: \.self) { type in + Text(type.rawValue).tag(type as ClothingType?) + } + } + .padding(.vertical) + .pickerStyle(.segmented) + + Picker("Style", selection: $selectedColor) { + Text("All").tag(String?.none) + .foregroundStyle(Color(hex: "#2C4C52")) + Text("Active").tag("Active" as String?) + Text("Classic").tag("Classic" as String?) + Text("Casual").tag("Casual" as String?) + Text("Blue").tag("Blue" as String?) + } + } + .padding(.vertical) + .foregroundStyle(Color(hex: "#2C4C52")) + + .pickerStyle(.segmented) + + HStack { + Text("$0") + Slider(value: Binding(get: { + Double(maxPrice) + }, set: { newValue in + maxPrice = Int(newValue) + }), in: 0...500, step: 50) // Only allow integer values + .tint(Color(hex: "#2C4C52")) + + Text("$\(maxPrice)") + } + .foregroundStyle(Color(hex: "#2C4C52")) + .padding(.horizontal) + } + .padding(.horizontal) + + HStack { + Text("Shop Shoes") + .font(.title2) + .fontWeight(.bold) + Spacer() + } + .padding() + + + + LazyVGrid(columns: columns) { + ForEach(filteredItems) { clothingItem in + NavigationLink(destination: ProductView(productImage: clothingItem.imageName, productName: clothingItem.name, productPrice: clothingItem.price).onAppear { + }.onDisappear { + }) { + ClothCard(width: 160, height: 150, clothingItem: clothingItem) + } + } + } + Spacer() + } + + } + + .tint(Color(hex: "#2C4C52")) + } + } + + + +#Preview { + GenShoesView() +} + + diff --git a/Rethread/Rethread/Views/GenTopsView.swift b/Rethread/Rethread/Views/GenTopsView.swift new file mode 100644 index 0000000..21ea8dc --- /dev/null +++ b/Rethread/Rethread/Views/GenTopsView.swift @@ -0,0 +1,110 @@ + +import SwiftUI + + + +struct GenTopsView: View { + + + @State private var selectedType: ClothingType? = nil + @State private var selectedColor: String? = nil + @State private var maxPrice: Int = 500 + + let columns: [GridItem] = [ + GridItem(.flexible()), + GridItem(.flexible()), + ] + var filteredItems: [ClothingItem] { + ArcteryxItems.filter { item in + (selectedType == nil || item.type == selectedType) && + (selectedColor == nil || item.color == selectedColor) && + item.price <= maxPrice + } + } + + + var body: some View { + NavigationStack { + ScrollView(showsIndicators: false) { + VStack { + Image("tshirtCover") + .resizable() + .aspectRatio(contentMode: .fill) + } + Spacer() + + VStack(alignment: .leading) { + VStack { + Picker("Type", selection: $selectedType) { + Text("All").tag(ClothingType?.none) + ForEach(ClothingType.allCases, id: \.self) { type in + Text(type.rawValue).tag(type as ClothingType?) + } + } + .padding(.vertical) + .pickerStyle(.segmented) + + Picker("Style", selection: $selectedColor) { + Text("All").tag(String?.none) + .foregroundStyle(Color(hex: "#2C4C52")) + Text("Active").tag("Active" as String?) + Text("Classic").tag("Classic" as String?) + Text("Casual").tag("Casual" as String?) + Text("Blue").tag("Blue" as String?) + } + } + .padding(.vertical) + .foregroundStyle(Color(hex: "#2C4C52")) + + .pickerStyle(.segmented) + + HStack { + Text("$0") + Slider(value: Binding(get: { + Double(maxPrice) + }, set: { newValue in + maxPrice = Int(newValue) + }), in: 0...500, step: 50) // Only allow integer values + .tint(Color(hex: "#2C4C52")) + + Text("$\(maxPrice)") + } + .foregroundStyle(Color(hex: "#2C4C52")) + .padding(.horizontal) + } + .padding(.horizontal) + + HStack { + Text("Shop T-Shirts") + .font(.title2) + .fontWeight(.bold) + Spacer() + } + .padding() + + + + LazyVGrid(columns: columns) { + ForEach(filteredItems) { clothingItem in + NavigationLink(destination: ProductView(productImage: clothingItem.imageName, productName: clothingItem.name, productPrice: clothingItem.price).onAppear { + }.onDisappear { + }) { + ClothCard(width: 160, height: 150, clothingItem: clothingItem) + } + } + } + Spacer() + } + + } + + .tint(Color(hex: "#2C4C52")) + } + } + + + +#Preview { + GenTopsView() +} + diff --git a/Rethread/Rethread/Views/HomeView.swift b/Rethread/Rethread/Views/HomeView.swift deleted file mode 100644 index f1d32c6..0000000 --- a/Rethread/Rethread/Views/HomeView.swift +++ /dev/null @@ -1,317 +0,0 @@ -// HomeView.swift - -import SwiftUI -import MapKit - -struct HomeView: View { - var body: some View { - TabView { - Group { - ZStack { - ScrollView(.vertical, showsIndicators: false) { - VStack { - HomeBarView() - - MainSearchBar() - - ScrollText() // This is just the"sustainable brands text" - BrandCardScrollView() - - ShopByClothingText() - - ClothingCardView() - - SaveWithUsText() - - ScrollView(.horizontal, showsIndicators: false) { - HStack { - ForEach (0 ..< 3) { index in - ClothCard(width: 150, height: 150, clothingItem: Image("sweatshirt") // This isnt the "shop by clothing card" its the real clothing - )} - } - } - .padding(.horizontal) - - - } - } - - } - .padding(.bottom) - .tabItem { - Image(systemName: "house") - } - MapView() - .tabItem { - Spacer() - Image(systemName: "qrcode") - - } - - MapView() - .tabItem { - Image(systemName: "mappin.circle.fill") - } - MapView() - .tabItem { - Image(systemName: "person") - .padding(.vertical) - } - .foregroundStyle(.green) - } - .accentColor(.purple) - .toolbarBackground(.white, for: .tabBar) - - - - } - } -} - -#Preview { - HomeView() -} - -struct HomeBarView: View { - @State var isShowingSheet = false - var body: some View { - HStack { - Text("Hey Morteza!") - .font(.title2) - .titleText() - Spacer() - Button { - isShowingSheet.toggle() - } label: { - Image(systemName: "slider.horizontal.3") - .foregroundStyle(Color(hex: "#2C4C52")) - } - .sheet(isPresented: $isShowingSheet, content: { - FilterView() - .presentationDetents([.medium]) - }) - - - } - .padding(.horizontal) - } -} - - - -extension Color { - init(hex: String) { - var cleanHexCode = hex.trimmingCharacters(in: .whitespacesAndNewlines) - cleanHexCode = cleanHexCode.replacingOccurrences(of: "#", with: "") - print(cleanHexCode) - var rgb: UInt64 = 0 - - Scanner(string: cleanHexCode).scanHexInt64(&rgb) - - let redValue = Double((rgb >> 16) & 0xFF) / 255.0 - let greenValue = Double((rgb >> 8) & 0xFF) / 255.0 - let blueValue = Double(rgb & 0xFF) / 255.0 - self.init(red: redValue, green: greenValue, blue: blueValue) - } -} - -struct MainSearchBar: View { - @State private var search: String = "" - var body: some View { - HStack { - HStack { - TextField("Search Clothes", text: $search) - Image(systemName: "magnifyingglass") - .foregroundStyle(Color(hex: "#2C4C52")) - - } - .padding(.vertical, 10) - .padding(.horizontal, 10) - .background(.white) - .cornerRadius(5) - .overlay( - RoundedRectangle(cornerSize: CGSize(width: 5, height: 5)) - .stroke(Color(hex: "#2C4C52")) - ) - } - .padding() - - - } -} - -struct ScrollText: View { - var body: some View { - HStack { - Text("Sustainable Brands") - .titleText() - - } - .frame(maxWidth: /*@START_MENU_TOKEN@*/.infinity/*@END_MENU_TOKEN@*/, alignment: .leading) - .padding(.horizontal) - } -} - -struct SaveWithUsText: View { - var body: some View { - HStack { - Text("Save With Us!") - .titleText() - Spacer() - NavigationStack { - NavigationLink(destination: ProductView()) { - Text("View All") - .foregroundStyle(Color(hex: "#2C4C52")) - .fontWeight(.semibold) - .underline() - } - } - - } - .padding(.horizontal) - } -} - -struct FilterView: View { - var body: some View { - VStack { - CustomDropdownMenu(items: [ - DropdownItem(id: 1, title: "Category", onSelect: {}), - DropdownItem(id: 2, title: "Medium", onSelect: {}), - DropdownItem(id: 3, title: "Large", onSelect: {}), - DropdownItem(id: 4, title: "X-Large", onSelect: {}), - ]) - .frame(maxHeight: .maximum(100, 100)) - - - CustomDropdownMenu(items: [ - DropdownItem(id: 1, title: "Category", onSelect: {}), - DropdownItem(id: 2, title: "Medium", onSelect: {}), - DropdownItem(id: 3, title: "Large", onSelect: {}), - DropdownItem(id: 4, title: "X-Large", onSelect: {}), - ]) - .frame(maxHeight: .maximum(100, 100)) - - - } - .padding() - } -} - -struct BrandImageCardView: View { - let brandCard: Image - var body: some View { - HStack { - brandCard - .brandCard() - } - } -} - -struct ClothingImageCardView: View { - let clothingCard: Image - var body: some View { - HStack { - clothingCard - .clothingCard() - } - } -} - - -struct BrandCardScrollView: View { - var body: some View { - ScrollView (.horizontal, showsIndicators: false) { - HStack{ - ForEach(0 ..< 3) { index in - BrandImageCardView(brandCard: Image("brandCard_\(index + 1)")) - } - } - } - .padding(.horizontal) - .padding(.bottom) - } -} - -// MARK: EXTENSIONS -extension Image { - func brandCard() -> some View { - self - .resizable() - .frame(width: 200, height: 110) - .clipShape(RoundedRectangle(cornerRadius: 5)) - } -} - -extension Image { - func clothingCard() -> some View { - self - .resizable() - .frame(width: 100, height: 250) - .clipShape(RoundedRectangle(cornerRadius: 5)) - } - -} - -extension Text { - func titleText() -> some View { - self - .foregroundStyle(Color(hex: "#2C4C52")) - .fontWeight(.semibold) - .font(.title3) - } -} - -struct ShopByClothingText: View { - var body: some View { - Text("Shop By Clothing") - .titleText() - .frame(maxWidth: /*@START_MENU_TOKEN@*/.infinity/*@END_MENU_TOKEN@*/, alignment: .leading) - .padding(.horizontal) - } -} - -struct ClothingCardView: View { - var body: some View { - ScrollView(.horizontal, showsIndicators: false) { - HStack { - ForEach (0 ..< 4) { index in - ClothingImageCardView(clothingCard: Image ("clothingCard_1")) - } - } - } - .padding(.horizontal) - .padding(.bottom) - } -} - -struct ClothCard: View { - let width: CGFloat - let height: CGFloat - let clothingItem: Image - var body: some View { - VStack (alignment: .leading) { - clothingItem - .resizable() - .frame(width: width, height: height) - .clipShape(RoundedRectangle(cornerRadius: 8)) - Text("Sweat Shirt") - .font(.subheadline) - Text("$55") - .font(.subheadline) - } - } -} - -struct BottomNavBarItem: View { - let image: Image - let action: ()-> Void - var body: some View { - Button(action: action, label: { - image - .frame(maxWidth: .infinity) - .foregroundStyle(Color(hex: "#2C4C52")) - .fontWeight(.semibold) - }) - } -} diff --git a/Rethread/Rethread/Views/MainView.swift b/Rethread/Rethread/Views/MainView.swift index 768983d..e5d4892 100644 --- a/Rethread/Rethread/Views/MainView.swift +++ b/Rethread/Rethread/Views/MainView.swift @@ -1,109 +1,467 @@ +// HomeView.swift + import SwiftUI -import NavigationTransitions +import MapKit +import PhotosUI + +struct HomeView: View { + + + + + var body: some View { + ScrollView(.vertical, showsIndicators: false) { + VStack { + HomeBarView() + + SliderView() + + Text("We Connect You to Sustainable Brands") + .fontWeight(.semibold) + .font(.largeTitle) + .padding(.horizontal) + .padding(.top, 50) + + BrandCardScrollView() + + Yap() + .padding() + + DiscoverDealsLink() + + HStack { + ClothCardDiscounted(width: 150, height: 150, clothingItem: Image("patagoniaQuar"), discount: "$120", oldPrice: "$180") + .padding() -#if canImport(UIKit) -extension View { - func hideKeyboard() { - UIApplication.shared.sendAction(#selector(UIResponder.resignFirstResponder), to: nil, from: nil, for: nil) + ClothCardDiscounted(width: 150, height: 150, clothingItem: Image("cotoTaxi"), discount: "$75", oldPrice: "$240") + .padding() + } + } + } } } -#endif + struct MainView: View { - @State private var path: [String] = [] - - var body: some View { - NavigationStack (path: $path) { - ZStack (alignment: .bottom) { - // Add Image - Image("flowerMainPage") - .resizable() - .overlay(Color.black.opacity(0.1)) - .clipped() - .edgesIgnoringSafeArea(.all) - .padding(.bottom, 220) - - // Botom Part - VStack (spacing: 50) { - - HStack { - Text("Get involved with" + "\n" + "sustainable fashion") - .font(.system(size: 20)) - .fontWeight(.semibold) - .foregroundColor(Color.primaryDark) - .opacity(0.5) - .multilineTextAlignment(.leading) - .lineSpacing(6) - Spacer() - } - .padding(.horizontal, 35) - .padding(.top, 25) - - - - VStack (spacing: 17) { - Button(action: { - path.append("SignInView") - }) { - HStack { - Text("Log In") - } - .frame(maxWidth: .infinity, maxHeight: .infinity) - } - .buttonStyle(PrimaryButtonStyle(width: 300)) - - HStack { - Spacer() - - Button(action: { - path.append("SignUpView") - }) { - Text("Create Account") - .foregroundColor(Color.primaryDark) - .fontWeight(.semibold) - .underline() - } - } - .padding(.horizontal, 35) + + @EnvironmentObject var viewModel: AuthViewModel + + @State private var isTabBarHidden: Bool = false + @State var selectedTab: Int = 100 + + + @ViewBuilder + var tabViews: some View { + + NavigationStack { + HomeView() + } + .tabItem { + Image(systemName: "house") + } + .tag(1) + + NavigationStack { + ScannerView() + } + .tabItem { + Image(systemName: "qrcode") + } + .tag(2) + + ReelView() + .tabItem { + Image(systemName: "movieclapper") + } + .tag(0) + + + + NavigationStack { + MapView() + } + .tabItem { + Image(systemName: "mappin.circle.fill") + } + .tag(3) + + NavigationStack { + ProfileView() + } + .tabItem { + Image(systemName: "person") + } + .tag(4) + } + + var body: some View { + TabView(selection: $selectedTab) { + tabViews + .tint(nil) + .toolbarBackground(selectedTab == 0 ? .black : .white, for: .tabBar) + .toolbarBackground(.visible, for: .tabBar) + } + .tint(selectedTab == 0 ? .white : Color(hex: "#2C4C52")) + + } +} + +#Preview { + MainView() +} + + +struct ButtonDestination { + var destination: AnyView +} + +struct SliderView: View { + let buttonDestinations: [ButtonDestination] = [ + ButtonDestination(destination: AnyView(aboutPatagoniaBrandView())), + ButtonDestination(destination: AnyView(aboutArcteryxBrandView(isTabBarHidden: .constant(true)))), + ButtonDestination(destination: AnyView(ScannerView())), + + ] + let images = ["Patagonia", "Arcteryx", "brokenplanet"] + public let timer = Timer.publish(every: 3, on: .main, in: .common).autoconnect() + @State private var selectedIndex = 0 + + var body: some View { + ZStack(alignment: .leadingLastTextBaseline) { + TabView(selection: $selectedIndex) { + ForEach(0..> 16) & 0xFF) / 255.0 + let greenValue = Double((rgb >> 8) & 0xFF) / 255.0 + let blueValue = Double(rgb & 0xFF) / 255.0 + self.init(red: redValue, green: greenValue, blue: blueValue) + } +} + + + + +struct SaveWithUsText: View { + var body: some View { + HStack { + Text("Save With Us!") + .titleText() + Spacer() + NavigationStack { + NavigationLink(destination: GenTopsView()) { + Text("View All") + .foregroundStyle(Color(hex: "#2C4C52")) + .fontWeight(.semibold) + .underline() + } + } + + } + .padding(.horizontal) + } +} + + +struct ClothingImageCardView: View { + let clothingCard: Image + var body: some View { + HStack { + clothingCard + .clothingCard() + } + } +} + + + +// MARK: EXTENSIONS + +extension Image { + func clothingCard() -> some View { + self + .resizable() + .frame(width: 100, height: 250) + .clipShape(RoundedRectangle(cornerRadius: 5)) + } + +} + +extension Text { + func titleText() -> some View { + self + .foregroundStyle(Color(hex: "#2C4C52")) + .fontWeight(.semibold) + .font(.title3) + } +} + +struct ShopByClothingText: View { + var body: some View { + Text("Shop By Clothing") + .titleText() + .frame(maxWidth: /*@START_MENU_TOKEN@*/.infinity/*@END_MENU_TOKEN@*/, alignment: .leading) + .padding(.horizontal) + } +} + +struct ClothingCardView: View { + var body: some View { + ScrollView(.horizontal, showsIndicators: false) { + HStack { + ForEach (0 ..< 4) { index in + ClothingImageCardView(clothingCard: Image ("clothingCard_1")) + } + } + } + .padding(.horizontal) + .padding(.bottom) + } +} + +struct PageIndicator: View { + @Binding var currentIndex: Int + let count: Int + + var body: some View { + HStack(spacing: 8) { + ForEach(0.. some View { + switch index { + case 1: + GenAccessoriesView() + .navigationTitle("Accessories") + case 2: + GenTopsView() + .navigationTitle("T-Shirts") + case 3: + GenBottomsView() + .navigationTitle("Pants") + case 4: + GenShoesView() + .navigationTitle("Shoes") + default: + Text("Default View") + } + } +} + +struct BrandImageCardView: View { + let brandCard: Image + let height: CGFloat + var body: some View { + HStack { + brandCard + .brandCard(height: height) + } + } +} + +extension Image { + func brandCard(height: CGFloat) -> some View { + self + .resizable() + .frame(width: .infinity, height: height) + .clipShape(RoundedRectangle(cornerRadius: 5)) + .padding(.bottom, 5) +// .shadow(color: .gray, radius: 2, x: 5, y: 5) + + } +} + + +struct Yap: View { + var body: some View { + Text("reThread knows what you love, so you can stay sustianable while still looking great.") + .multilineTextAlignment(.center) + .fontWeight(.semibold) + .font(.largeTitle) + + } +} + +struct Line: View { + var body: some View { + VStack { + Divider().background(Color.gray) + .frame(height: 4) + .overlay(.red) + } + .frame(width: 70) + .padding() + } +} + +struct ClothCard: View { + let width: CGFloat + let height: CGFloat + let clothingItem: ClothingItem + var body: some View { + VStack (alignment: .leading) { + Image(clothingItem.imageName) + .resizable() + .frame(width: width, height: height) + .clipShape(RoundedRectangle(cornerRadius: 8)) + Text(clothingItem.name) + .font(.subheadline) + Text("$\(clothingItem.price)") + .font(.subheadline) + .padding(.bottom, 20) + } + } +} + +struct ClothCardDiscounted: View { + let width: CGFloat + let height: CGFloat + let clothingItem: Image + let discount: String + let oldPrice: String + var body: some View { + VStack (alignment: .leading) { + clothingItem + .resizable() + .frame(width: width, height: height) + .clipShape(RoundedRectangle(cornerRadius: 8)) + Text("Active Wear") + .font(.subheadline) + HStack { + Text(discount) + .font(.subheadline) + .foregroundStyle(.red) + Text(oldPrice) + .font(.subheadline) + .strikethrough() + } } - .navigationTransition(.slide(axis: .vertical)) - // Safe area for iPhone X and above - .edgesIgnoringSafeArea(.all) // This will extend the content to the edges - .background(Color(UIColor.systemGray6)) - .overlay( - GeometryReader { geometry in - Color.white.opacity(0.3) // Adjust the opacity here for semi-transparency - .frame(width: geometry.size.width, height: geometry.safeAreaInsets.top) - .edgesIgnoringSafeArea(.top) - }, alignment: .top - ) } } -#if DEBUG -struct MainView_Previews: PreviewProvider { - static var previews: some View { - MainView() + +struct DiscoverDealsLink: View { + var body: some View { + VStack { + Text("Because You Love the Outdoors") + .multilineTextAlignment(.center) + .font(.title) + + + NavigationStack { + NavigationLink(destination: GenTopsView()) { + Text("View All") + .font(.title2) + .foregroundStyle(.red) + } + } + + + } + .padding() + .border(Color(hex: "#2C4C52"), width: 4) } } -#endif +struct CustomBackButtonView: View { + @Environment(\.presentationMode) var presentationMode + + + var body: some View { + Button(action: { + self.presentationMode.wrappedValue.dismiss() + }) { + Image(systemName: "arrow.left") // Replace with your custom image + .aspectRatio(contentMode: .fit) + .foregroundColor(Color(hex: "#2C4C52")) // Customize as needed + } + } +} diff --git a/Rethread/Rethread/Views/MapView.swift b/Rethread/Rethread/Views/MapView.swift index 998084f..c8d1727 100644 --- a/Rethread/Rethread/Views/MapView.swift +++ b/Rethread/Rethread/Views/MapView.swift @@ -1,5 +1,4 @@ // MapView.swift - import SwiftUI import MapKit import CoreLocation @@ -7,45 +6,207 @@ import CoreLocation struct MapView: View { @StateObject private var viewModel = MapViewModel() // MapViewModel can be fouund in Models/MapViewModels in the directory @State private var cameraPos: MapCameraPosition = .userLocation(fallback: .automatic) - var body: some View { + @State private var mapSelection: MKMapItem? + @State private var viewingRegion: MKCoordinateRegion? + + @State private var searchText: String = "" + @State private var showSearch: Bool = false + @State private var searchResults: [MKMapItem] = [] + + @State private var showDetails: Bool = false + @State private var lookAroundScene: MKLookAroundScene? - VStack { - Text("Use your current postal code or enter a new one to see locations near you!") - .padding() - .foregroundStyle(Color(hex: "#2C4C52")) + @State private var routeDisplaying: Bool = false + @State private var route: MKRoute? + @State private var routeDestination: MKMapItem? - LocationSearchBar() + var body: some View { - Text("Locations Around you") - .frame(maxWidth: .infinity, alignment: .leading) - .padding(.horizontal) - .foregroundStyle(Color(hex: "#2C4C52")) - CustomDropdownMenu(items: [ - DropdownItem(id: 1, title: "24 Ave. NW", onSelect: {}), - DropdownItem(id: 2, title: "32 Deer foot trail NE", onSelect: {}), - DropdownItem(id: 3, title: "18 Blvd. Road W", onSelect: {}) - ]) - .zIndex(1000) - .frame(maxHeight: .maximum(100, 100)) - .padding(.horizontal) +// VStack { +// Text("meow") +// } + NavigationStack { + + Map(position: $cameraPos, selection: $mapSelection) { + + ForEach(searchResults, id: \.self) { mapItem in + if routeDisplaying { + if mapItem == routeDestination { + let placemark = mapItem.placemark + Marker(placemark.name ?? "Place", coordinate: placemark.coordinate) + .tint(Color(hex: "#2C4C52")) + } + } else { + let placemark = mapItem.placemark + Marker(placemark.name ?? "Place", coordinate: placemark.coordinate) + .tint(Color(hex: "#2C4C52")) + } + } + + if let route { + MapPolyline(route.polyline) + .stroke(.blue, lineWidth: 7) + } + + } + .onMapCameraChange({ ctx in + viewingRegion = ctx.region + }) + .searchable(text: $searchText, isPresented: $showSearch) + .navigationTitle("Brands Near You!") + .accentColor(Color(hex: "#2C4C52")) + .mapControls { + MapCompass() + MapUserLocationButton() + MapPitchToggle() + } + .toolbar(routeDisplaying ? .hidden : .visible, for: .navigationBar) + .sheet(isPresented: $showDetails, onDismiss: { + withAnimation(.snappy) { + if let boundingRect = route?.polyline.boundingMapRect, routeDisplaying { + cameraPos = .rect(boundingRect) + } + } + }, content: { + MapDetails() + .presentationDetents([.height(300)]) + .presentationBackgroundInteraction(.enabled(upThrough: .height(300))) + .presentationCornerRadius(25) + .interactiveDismissDisabled(true) + }) + .safeAreaInset(edge: .bottom) { + if routeDisplaying { + Button("End Route") { + withAnimation(.snappy) { + routeDisplaying = false + showDetails = true + mapSelection = routeDestination + routeDestination = nil + route = nil + cameraPos = .region(viewModel.region) + } + } + .foregroundStyle(.white) + .frame(maxWidth: .infinity) + .padding(.vertical, 12) + .background(.red.gradient, in: .rect(cornerRadius: 15)) + .padding() + .background(.ultraThinMaterial) + + } + } + .onSubmit(of: .search) { + print("Search submitted for: \(searchText)") + Task { + guard !searchText.isEmpty else { return } + print("Starting search...") + await searchPlaces() + } + } + .onChange(of: showSearch, initial: false) { + if !showSearch { + searchResults.removeAll(keepingCapacity: false) + showDetails = false + + withAnimation(.snappy) { + cameraPos = .region(viewModel.region) + } + } + } + .onChange(of: mapSelection) { oldValue, newValue in + showDetails = newValue != nil + fetchLookAroundData() + } + } - Map(position: $cameraPos) { + } + @ViewBuilder + func MapDetails() -> some View { + VStack(spacing: 15) { + ZStack { + if lookAroundScene == nil { + ContentUnavailableView("No Preview Available", systemImage: "eye.slash") + } else { + LookAroundPreview(scene: $lookAroundScene) + } } - .mapControls { - MapCompass() - MapUserLocationButton() - MapPitchToggle() - } - .accentColor(Color(hex: "#2C4C52")) - .onAppear { - viewModel.isUserLocationOn() + .frame(height: 200) + .clipShape(.rect(cornerRadius: 15)) + .overlay(alignment: .topTrailing) { + Button(action: { + showDetails = false + withAnimation(.snappy) { + mapSelection = nil + } + }, label: { + Image(systemName: "xmark.circle.fill") + .font(.title) + .foregroundStyle(.black) + .background(.white, in:.circle) + }) } + + Button("Get Directions", action: fetchRoute) + .foregroundStyle(.white) + .frame(maxWidth: .infinity) + .padding(.vertical, 12) + .background(.blue.gradient, in: .rect(cornerRadius: 15)) + } + .padding(15) + } + + + + func searchPlaces() async { + print("Starting search for: \(searchText)") + + let request = MKLocalSearch.Request() + request.naturalLanguageQuery = searchText + request.region = viewingRegion ?? viewModel.region + + do { + let response = try await MKLocalSearch(request: request).start() + searchResults = response.mapItems + print("Search completed. Found \(searchResults.count) results.") + } catch { + print("Search failed with error: \(error)") } + } + + + /// Fetching Look Around data :) + + func fetchLookAroundData() { + guard let mapSelection else { return } + lookAroundScene = nil + Task { + let request = MKLookAroundSceneRequest(mapItem: mapSelection) + lookAroundScene = try? await request.scene + } + } + + + func fetchRoute() { + guard let mapSelection else { return } + let request = MKDirections.Request() + request.source = .init(placemark: .init(coordinate: viewModel.locationManager.location?.coordinate ?? CLLocationCoordinate2D(latitude: 37.331516, longitude: -121.891054))) + request.destination = mapSelection + + Task { + let result = try? await MKDirections(request: request).calculate() + route = result?.routes.first + routeDestination = mapSelection + withAnimation(.snappy) { + routeDisplaying = true + showDetails = false + + } + } } } @@ -80,11 +241,6 @@ struct LocationSearchBar: View { - - - - - #Preview { MapView() } diff --git a/Rethread/Rethread/Views/ProductView.swift b/Rethread/Rethread/Views/ProductView.swift index 41ff105..b991bd8 100644 --- a/Rethread/Rethread/Views/ProductView.swift +++ b/Rethread/Rethread/Views/ProductView.swift @@ -2,29 +2,40 @@ import SwiftUI + struct ProductView: View { + @State var productImage: String? + @State var productName: String? + @State var productPrice: Int? + + var body: some View { ZStack { ScrollView { - Image("sweatshirt") + Image(productImage ?? "globe") .resizable() .aspectRatio(contentMode: .fill) - .ignoresSafeArea(edges: .top) - DescriptionView() + + DescriptionView(productName: productName) .offset(y: -40) Spacer() } HStack { - Text("$50") + Text("$" + String(productPrice ?? 60)) .font(.title) .fontWeight(.bold) .foregroundStyle(.white) Spacer() - Button(action: {}, label: { + Button(action: { + if let url = URL(string: "https://arcteryx.com/ca/en/shop/mens/beta-jacket-8584") { + UIApplication.shared.open(url) + } + }, label: { Text("Buy now") + .fontWeight(.bold) .foregroundStyle(Color(hex: "#2C4C52")) .padding() .padding(.horizontal) @@ -38,8 +49,7 @@ struct ProductView: View { .clipShape(UnevenRoundedRectangle(cornerRadii: RectangleCornerRadii(topLeading: 40))) .frame(maxHeight: .infinity, alignment: .bottom) } - .ignoresSafeArea(edges: .bottom) - +// .ignoresSafeArea(edges: .bottom) } } #Preview { @@ -47,10 +57,12 @@ struct ProductView: View { } struct DescriptionView: View { + @State var productName: String? + var body: some View { VStack (alignment: .leading) { HStack { - Text("Sweatshirt") + Text(productName ?? "Placeholder") .font(.title) .fontWeight(.bold) Spacer() @@ -68,7 +80,6 @@ struct DescriptionView: View { DropdownItem(id: 1, title: "Small", onSelect: {}), DropdownItem(id: 2, title: "Medium", onSelect: {}), DropdownItem(id: 3, title: "Large", onSelect: {}), - DropdownItem(id: 4, title: "X-Large", onSelect: {}), ]) .zIndex(10000000) diff --git a/Rethread/Rethread/Views/ProfileView.swift b/Rethread/Rethread/Views/ProfileView.swift index 306f76a..a2e9f37 100644 --- a/Rethread/Rethread/Views/ProfileView.swift +++ b/Rethread/Rethread/Views/ProfileView.swift @@ -1,51 +1,95 @@ // ProfileView.swift import SwiftUI +import PhotosUI + + + +enum SectionType { + case promotions + case accountSettings + case notifications + case logout +} + + +extension SectionType { + + @ViewBuilder func view(viewModel: AuthViewModel) -> some View { + + switch self { + case .promotions: + MainView() + case .accountSettings: + AccountSettingsView() + case .notifications: + AccountNotificationView() + case .logout: + Button(action: { + Task { + await viewModel.signOut() + } + }, label: { + Text("Log Out") + .foregroundStyle(.white) + }) + .buttonStyle(.borderedProminent) + .tint(.red) + } + } +} struct ProfileView: View { + @EnvironmentObject var viewModel: AuthViewModel + @State private var profileName: String = "Parsa Kargari" - - var sections: [Sections] = [ - .init(name: "Points and Promotions", icon: "ticket", color: Color(hex: "#2C4C52")), + @State private var profileImage: UIImage? = UIImage(named: "king") - .init(name: "Account Settings", icon: "pencil", color: Color(hex: "#2C4C52")), + var sections: [Sections] = [ + .init(name: "Points and Promotions", icon: "ticket", color: Color(hex: "#2C4C52"), destinations: .promotions), - .init(name: "Notifications", icon: "bell", color: Color(hex: "#2C4C52")), - ] + .init(name: "Account Settings", icon: "pencil", color: Color(hex: "#2C4C52"), destinations: .accountSettings), + .init(name: "Notifications", icon: "bell", color: Color(hex: "#2C4C52"), destinations: .notifications), + .init(name: "Log Out", icon: "door.right.hand.open", color: Color(hex: "#2C4C52"), destinations: .logout), + ] var body: some View { - VStack { - Image("king") - .resizable() - .aspectRatio(contentMode: .fit) - .frame(width: 160) - .border(Color(hex: "#2C4C52"), width: 5) - .cornerRadius(5) - .padding() - Text(profileName) - .padding() - .foregroundStyle(Color(hex: "#2C4C52")) NavigationStack { + VStack { + ZStack(alignment: .bottomTrailing) { + Image(uiImage: profileImage ?? UIImage()) + .resizable() + .aspectRatio(contentMode: .fill) + .frame(maxWidth: 160, maxHeight: 160) + .border(Color(hex: "#2C4C52"), width: 5) + .cornerRadius(5) + .padding() + PhotoPicker(image: $profileImage) + + } + Text(profileName) + .font(.title2) + .fontWeight(.bold) + .foregroundStyle(Color(hex: "#2C4C52")) + CameraPicker(image: $profileImage) + .padding(.bottom) + } + List { ForEach(sections, id: \.name) { section in - NavigationLink(value: section){ + NavigationLink(destination: section.destinations.view(viewModel: viewModel)) { Label(section.name, systemImage: section.icon) .foregroundStyle(section.color) } } } - .navigationDestination(for: Sections.self) { section in - VStack { - Image(systemName: "globe") - .foregroundStyle(section.color) - } - } + .listStyle(.insetGrouped) } - } + } } @@ -53,8 +97,68 @@ struct Sections: Hashable { let name: String let icon: String let color: Color + let destinations: SectionType +} + + +struct PhotoPicker: View { + @State private var selectedItem: PhotosPickerItem? + @Binding var image: UIImage? + + var body: some View { + + VStack { + + PhotosPicker(selection: $selectedItem, matching: .images) { + Image(systemName: "square.and.pencil.circle.fill") + .resizable() + .frame(width: 30, height: 30) + .padding(5) + .foregroundStyle(.white) + .background(Color(hex: "#2C4C52")) + .clipShape(Circle(), style: FillStyle()) + } + .photosPickerStyle(.presentation) + .onChange(of: selectedItem) { + Task { + if let data = try? await selectedItem?.loadTransferable(type: Data.self) { + image = UIImage(data: data) + } else { + print("Failed to load the image") + } + } + } + } + } } +struct CameraPicker: View { + @State private var showCamera = false + @State private var selectedImage: UIImage? + @Binding var image: UIImage? + var body: some View { + VStack { + if let selectedImage{ + Image(uiImage: selectedImage) + .resizable() + .scaledToFit() + } + + Button(action: { + self.showCamera.toggle() + + }, label: { + Text("Open camera") + Image(systemName: "camera") + }) + .tint(.gray) + .buttonStyle(.borderedProminent) + .fullScreenCover(isPresented: self.$showCamera) { + accessCameraView(selectedImage: self.$selectedImage) + } + } + } +} #Preview { ProfileView() diff --git a/Rethread/Rethread/Views/ReelView.swift b/Rethread/Rethread/Views/ReelView.swift new file mode 100644 index 0000000..8b1824d --- /dev/null +++ b/Rethread/Rethread/Views/ReelView.swift @@ -0,0 +1,230 @@ +// +// ReelView.swift +// InstReels +// + +// + +import SwiftUI +import AVKit + +enum SideButton: CaseIterable { + case like, menu + + var image: Image { + switch self { + case .like: Image(systemName: "suit.heart") + case .menu: Image(systemName: "ellipsis") + } + } + +} + +struct ReelView: View { + @State private var selectedStyle: VideoType? = nil + + + var body: some View { + GeometryReader { proxy in + + let size = proxy.size + + TabView { + ForEach(fetchVideos().filter { video in + + return selectedStyle == .all || selectedStyle == nil || video.mediaFile.vidType == selectedStyle + }) + { reel in + ReelPlayer(reel: reel) + .frame(width: size.width) + .rotationEffect(.init(degrees: -90)) + .ignoresSafeArea(.all, edges: .top) + + } + } + .rotationEffect(.init(degrees: 90)) + .frame(width: size.height) + .tabViewStyle(.page(indexDisplayMode: .never)) + .frame(width: size.width) + .overlay( + Menu { + + Button("All") { + selectedStyle = .all + } + + ForEach(VideoType.allCases.filter { $0 != .all }, id: \.self) { type in + Button(action: { + selectedStyle = type + }) { + Text(type.rawValue) + .font(.title) + .fontWeight(.bold) + } + } + } label: { + HStack() { + Text(selectedStyle == .all ? "Styles" : selectedStyle?.rawValue ?? "Styles") + .font(.title) + .fontWeight(.heavy) + .foregroundColor(.white) + .padding(.leading,20) + Image(systemName: "chevron.down") + .foregroundStyle(.white) + .padding(.leading,-6) + } + }, + alignment: .topLeading + ) + + } + .ignoresSafeArea(.all, edges: .top) + + } + + private func fetchVideos() -> [Reel] { + Media.previews.map { item -> Reel in + let url = Bundle.main.path(forResource: item.url, ofType: "MP4") ?? Bundle.main.path(forResource: item.url, ofType: "mp4") ?? Bundle.main.path(forResource: item.url, ofType: "MOV") ?? Bundle.main.path(forResource: item.url, ofType: "mov") ?? "" + + let player = AVPlayer(url: URL(fileURLWithPath: url)) + return Reel(player: player, mediaFile: item) + } + } +} + +#Preview { + FullVidView() +} + +struct ReelPlayer: View { + let reel: Reel + + @State var readMore = false + var description = " Shall I compare thee to a summer’s day? Thou art more lovely and more temperate: Rough winds do shake the darling buds of May, And summer’s lease hath all too short a date" + + var body: some View { + ZStack(alignment: .bottomTrailing) { + + + + VideoPlayer(player: reel.player) + .onAppear { + reel.player.seek(to: CMTime.zero) + reel.player.play() + } + .onDisappear { + reel.player.pause() + } + + + VStack(alignment: .leading) { + + Spacer() + HStack(alignment: .bottom) { + Image("king") + .resizable() + .aspectRatio(contentMode: .fill) + .frame(width: 40, height: 40) + .clipShape(Circle(), style: /*@START_MENU_TOKEN@*/FillStyle()/*@END_MENU_TOKEN@*/) + + Text("Parsa_king420") + .font(.system(size: 16)) + .bold() + .foregroundStyle(.white) + .padding(.bottom, 10) + + Button(action: { + // + }, label: { + Text("Follow") + .font(.system(size: 16, weight: .semibold)) + .foregroundStyle(.white) + .padding(.horizontal, 10) + .padding(.vertical, 4) + .background { + RoundedRectangle(cornerRadius: 8) + .stroke(.white.opacity(0.7), lineWidth: 1) + } + + }) + .padding(.bottom, 6) + + } + + ZStack(alignment: .bottomLeading) { + if readMore { + ScrollView(.vertical, showsIndicators: false) { + Text(reel.mediaFile.title + description) + .font(.callout) + .fontWeight(.semibold) + .foregroundStyle(.white) + } + .frame(width: 300, height: 64) + } else { + + Button(action: { + withAnimation { readMore.toggle() } + }, label: { + HStack { + Text(reel.mediaFile.title) + .font(.callout) + .fontWeight(.semibold) + .foregroundStyle(.white) + .lineLimit(1) + + Text("more") + .font(.callout) + .bold() + .foregroundStyle(Color(uiColor: .systemGray2)) + } + .padding(.top, 6) + .frame(maxWidth: .infinity, alignment: .leading) + }) + + } + + } + } + .padding() + .frame(maxWidth: .infinity, maxHeight: .infinity, alignment: .leading) + + + + VStack(spacing: 20) { + ForEach(SideButton.allCases, id: \.self) { button in + makeSideButton(for: button, accessoryNumber: button == .menu || button == .menu ? 0 : (0...300).randomElement()!) + } + } + .padding() + + + + } + } +} + +extension ReelPlayer { + private func makeSideButton(for button: SideButton, accessoryNumber: Int) -> some View { + Button(action: { + // + }, label: { + VStack(spacing: 0) { + button.image + .font(.system(size: 24, weight: .semibold)) + .foregroundStyle(.white) + .padding(1) + + if accessoryNumber > 0 { + Text(String(accessoryNumber)) + .font(.caption) + .foregroundStyle(.white) + .bold() + } + + } + }) + } +} + + + diff --git a/Rethread/Rethread/Views/ScannerView.swift b/Rethread/Rethread/Views/ScannerView.swift new file mode 100644 index 0000000..457570a --- /dev/null +++ b/Rethread/Rethread/Views/ScannerView.swift @@ -0,0 +1,25 @@ +// ScannerView.swift + +import SwiftUI + +struct ScannerView: View { + @State private var uploadedImage: UIImage? + var body: some View { + VStack { + Text("You can earn points by scanning a sustainable tag. The camera recognizes the information and analyzes your purchase. Open the camera to take a picture. Or upload your own!") + .padding(.top, 100) + .padding(.horizontal,30) + .font(.title) + + CameraPicker(image: $uploadedImage) + .padding() + Spacer() + + } + + } +} + +#Preview { + ScannerView() +} diff --git a/Rethread/Rethread/Views/SignInView.swift b/Rethread/Rethread/Views/SignInView.swift index 06031cf..5bc8544 100644 --- a/Rethread/Rethread/Views/SignInView.swift +++ b/Rethread/Rethread/Views/SignInView.swift @@ -1,10 +1,14 @@ import SwiftUI import CustomTextField +struct SignInFormData { + var email: String = "" + var password: String = "" +} + struct SignInView: View { @Binding var path: [String] - @State private var email: String = "" - @State private var password: String = "" + @State private var formData = SignInFormData() @State private var isShowingVerification: Bool = false @State private var isPasswordVisible: Bool = false @FocusState var isFieldFocus: FieldToFocus? @@ -59,9 +63,9 @@ struct SignInView: View { VStack(alignment: .leading, spacing: 20) { - CustomField(text: $email, titleText: "Email", placeHolderText: "example@domain.com") + CustomField(text: $formData.email, titleText: "Email", placeHolderText: "example@domain.com") - CustomField(text: $password, titleText: "Password", placeHolderText: "Password", secureText: true) + CustomField(text: $formData.password, titleText: "Password", placeHolderText: "Password", secureText: true) Button(action: { // Handle forgot password action @@ -82,7 +86,29 @@ struct SignInView: View { // Bottom content, including the sign-in button VStack (spacing: 20) { Button("Sign In") { - self.isShowingVerification = true + Task { + try await viewModel.signInAndRetrievePhoneNumber(withEmail: formData.email, password: formData.password) { phoneNumber, error in + if let error = error { + // Handle error (e.g., show an alert) + print("Sign-in error: \(error.localizedDescription)") + } else if let phoneNumber = phoneNumber { + // Proceed with showing OTP verification view + print("Retrieved phone number: \(phoneNumber)") + Task { + try await viewModel.sendVerificationCode(phoneNumber: phoneNumber) { success, error in + if success { + self.isShowingVerification = true + } else { + print("DEBUG: Error sending verification code: \(error?.localizedDescription ?? "Unknown error")") + } + } + } + } else { + // No phone number found, handle accordingly + print("No phone number associated with this account.") + } + } + } } .buttonStyle(PrimaryButtonStyle(width: 300)) .padding(.bottom, 5) @@ -132,7 +158,7 @@ struct SignInView: View { .frame(maxWidth: .infinity, maxHeight: .infinity, alignment: .bottom) } .fullScreenCover(isPresented: $isShowingVerification) { - VerificationView(isSignIn: true, path: $path, userEmail: email, userPassword: password) + VerificationView(isSignIn: true, path: $path, signInData: $formData) } .gesture(TapGesture().onEnded{ self.hideKeyboard() @@ -141,11 +167,3 @@ struct SignInView: View { .navigationBarBackButtonHidden(true) } } - -#if DEBUG -struct SignInView_Previews: PreviewProvider { - static var previews: some View { - SignInView(path: .constant(["SignInView"])) - } -} -#endif diff --git a/Rethread/Rethread/Views/SignUpView.swift b/Rethread/Rethread/Views/SignUpView.swift index 58d7d92..dd63ae3 100644 --- a/Rethread/Rethread/Views/SignUpView.swift +++ b/Rethread/Rethread/Views/SignUpView.swift @@ -22,6 +22,7 @@ struct SignUpView: View { @State private var showingTermsAndConditions = false @State private var showingGenderPicker = false @State private var genderOptions = ["Male", "Female", "Other"] + @State private var tempSignInData = SignInFormData() @State private var areTermsAccepted = false @Environment(\.dismiss) private var dismiss @EnvironmentObject var viewModel: AuthViewModel @@ -148,19 +149,20 @@ struct SignUpView: View { // Bottom content, including the sign-in button VStack (spacing: 16) { Button("Join Us") { - // Handle sign up - print(formData) - - // Send verification code + // Assume validation passed Task { do { - self.isShowingVerification = true - } catch { - print("DEBUG: Error starting auth: \(error.localizedDescription)") + try await viewModel.sendVerificationCode(phoneNumber: "+14039918538") { success, error in + if success { + isShowingVerification.toggle() + } else { + print("DEBUG: Error sending verification code: \(error?.localizedDescription ?? "Unknown error")") + } + } } } - } + .buttonStyle(PrimaryButtonStyle(width: 300, isDisabled: !areTermsAccepted)) .disabled(!areTermsAccepted) @@ -189,7 +191,8 @@ struct SignUpView: View { } } .fullScreenCover(isPresented: $isShowingVerification) { - VerificationView(isSignIn: false, path: $path, formData: formData) + // Dummy signinData + VerificationView(isSignIn: false, path: $path, formData: formData, signInData: $tempSignInData) } .gesture(TapGesture().onEnded{ self.hideKeyboard() diff --git a/Rethread/Rethread/Views/VerificationView.swift b/Rethread/Rethread/Views/VerificationView.swift index a9fccae..32f5cc6 100644 --- a/Rethread/Rethread/Views/VerificationView.swift +++ b/Rethread/Rethread/Views/VerificationView.swift @@ -4,8 +4,7 @@ struct VerificationView: View { @State var isSignIn: Bool @Binding var path: [String] var formData: SignUpFormData? - var userEmail: String? - var userPassword: String? + @Binding var signInData: SignInFormData @Environment(\.dismiss) private var dismiss @EnvironmentObject var viewModel: AuthViewModel @State private var isLoading = false @@ -67,10 +66,12 @@ struct VerificationView: View { // MARK: SIGN IN OTP Task { do { - try await viewModel.signIn(withEmail: userEmail!, password: userPassword!) + // Verify OTP + try await viewModel.verifyPhoneNumber(verificationCode: otpCode) + try await viewModel.signIn(withEmail: signInData.email, password: signInData.password) isLoading = false - dismiss() } catch { + isLoading = false print("DEBUG: Error logging user in : \(error.localizedDescription)") } } @@ -78,13 +79,18 @@ struct VerificationView: View { // MARK: SIGN UP OTP Task { do { - try await viewModel.createUser(formData: formData!) + // Verify OTP + try await viewModel.verifyPhoneNumber(verificationCode: otpCode) + + // If no error was thrown, OTP verification was successful + try await viewModel.createUser(formData: formData!) isLoading = false - dismiss() } catch { - print("DEBUG: Error verifying user: \(error.localizedDescription)") + isLoading = false + print("DEBUG: Error verifying phone number or creating user: \(error.localizedDescription)") } } + } } .buttonStyle(PrimaryButtonStyle(width: 300, isDisabled: checkStates() || isLoading)) @@ -118,11 +124,3 @@ struct VerificationView: View { return false } } - -#if DEBUG -struct VerificationView_Previews: PreviewProvider { - static var previews: some View { - VerificationView(isSignIn: false, path: .constant([""]), formData: nil) - } -} -#endif diff --git a/Rethread/Rethread/Views/VideoPlayer.swift b/Rethread/Rethread/Views/VideoPlayer.swift new file mode 100644 index 0000000..5db6450 --- /dev/null +++ b/Rethread/Rethread/Views/VideoPlayer.swift @@ -0,0 +1,26 @@ +// +// VideoPlayer.swift +// InstReels +// +// + +import SwiftUI +import AVKit + +struct VideoPlayer: UIViewControllerRepresentable { + var player: AVPlayer + + func makeUIViewController(context: Context) -> AVPlayerViewController { + let controler = AVPlayerViewController() + controler.player = player + controler.showsPlaybackControls = false + controler.videoGravity = .resizeAspectFill + + return controler + } + + func updateUIViewController(_ uiViewController: AVPlayerViewController, context: Context) { + // + } +} + diff --git a/Rethread/Rethread/Views/aboutArc'teryxBrandView.swift b/Rethread/Rethread/Views/aboutArc'teryxBrandView.swift new file mode 100644 index 0000000..26bd1d1 --- /dev/null +++ b/Rethread/Rethread/Views/aboutArc'teryxBrandView.swift @@ -0,0 +1,132 @@ +// aboutArc'teryxBrandView.swift + + +import SwiftUI + + + +struct aboutArcteryxBrandView: View { + + @Binding var isTabBarHidden: Bool? + + + @State private var selectedType: ClothingType? = nil + @State private var selectedColor: String? = nil + @State private var maxPrice: Int = 500 + + let columns: [GridItem] = [ + GridItem(.flexible()), + GridItem(.flexible()), + ] + var filteredItems: [ClothingItem] { + ArcteryxItems.filter { item in + (selectedType == nil || item.type == selectedType) && + (selectedColor == nil || item.color == selectedColor) && + item.price <= maxPrice + } + } + + + var body: some View { + NavigationStack { + ScrollView(showsIndicators: false) { + VStack { + Image("arcHeader") + .resizable() + .aspectRatio(contentMode: .fill) + } + Spacer() + + VStack(alignment: .leading) { + Text("Arc'Teryx's commitment to sustainablity:") + .foregroundStyle(Color(hex: "#2C4C52")) + .font(.title2) + .fontWeight(.bold) + .padding() + Text("Arc'teryx, founded in 1989, emphasizes the use of durable and eco-friendly materials, and actively engages in environmental stewardship, striving for minimal environmental impact.") + .foregroundStyle(Color(hex: "#2C4C52")) + .italic() + .font(.subheadline) + .padding(.horizontal) + .padding(.bottom) + + + + VStack { + Picker("Type", selection: $selectedType) { + Text("All").tag(ClothingType?.none) + ForEach(ClothingType.allCases, id: \.self) { type in + Text(type.rawValue).tag(type as ClothingType?) + } + } + .pickerStyle(.segmented) + + Picker("Color", selection: $selectedColor) { + Text("All").tag(String?.none) + .foregroundStyle(Color(hex: "#2C4C52")) + Image(uiImage: ImageRenderer(content: Image(systemName: "circle.fill").foregroundStyle(.red)).uiImage!.withRenderingMode(.alwaysOriginal)) + .tag("Red" as String?) + Text("Blue").tag("Blue" as String?) + } + + } + .foregroundStyle(Color(hex: "#2C4C52")) + + .pickerStyle(.segmented) + + HStack { + Text("$0") + Slider(value: Binding(get: { + Double(maxPrice) + }, set: { newValue in + maxPrice = Int(newValue) + }), in: 0...500, step: 50) // Only allow integer values + .tint(Color(hex: "#2C4C52")) + + Text("$\(maxPrice)") + } + .foregroundStyle(Color(hex: "#2C4C52")) + .padding(.horizontal) + } + .padding(.horizontal) + + HStack { + Text("Shop") + .font(.title2) + .fontWeight(.bold) + Image("arcLetters") + .resizable() + .aspectRatio(contentMode: .fit) + .frame(width: 120, height: 30) + Spacer() + } + .padding(.horizontal) + + + + LazyVGrid(columns: columns) { + ForEach(filteredItems) { clothingItem in + NavigationLink(destination: ProductView(productImage: clothingItem.imageName, productName: clothingItem.name, productPrice: clothingItem.price).onAppear { + self.isTabBarHidden = true + }.onDisappear { + self.isTabBarHidden = false + }) { + ClothCard(width: 160, height: 150, clothingItem: clothingItem) + } + } + } + Spacer() + } + + } + .navigationTitle("Arc'Teryx") + + .tint(Color(hex: "#2C4C52")) + } + } + + +#Preview { + aboutArcteryxBrandView(isTabBarHidden: .constant(false)) +} + diff --git a/Rethread/Rethread/Views/aboutPatagoniaBrandView.swift b/Rethread/Rethread/Views/aboutPatagoniaBrandView.swift new file mode 100644 index 0000000..daf31ab --- /dev/null +++ b/Rethread/Rethread/Views/aboutPatagoniaBrandView.swift @@ -0,0 +1,121 @@ +// aboutBrandView.swift + +import SwiftUI + + + +struct aboutPatagoniaBrandView: View { + + + @State private var selectedType: ClothingType? = nil + @State private var selectedColor: String? = nil + @State private var maxPrice: Int = 500 + + let columns: [GridItem] = [ + GridItem(.flexible()), + GridItem(.flexible()), + ] + var filteredItems: [ClothingItem] { + allItems.filter { item in + (selectedType == nil || item.type == selectedType) && + (selectedColor == nil || item.color == selectedColor) && + item.price <= maxPrice + } + } + + + var body: some View { + ScrollView(showsIndicators: false) { + VStack { + Image("patagoniaHeader") + .resizable() + .aspectRatio(contentMode: .fill) + } + Spacer() + + VStack(alignment: .leading) { + Text("Patagonia's commitment to sustainablity:") + .foregroundStyle(Color(hex: "#2C4C52")) + .font(.title2) + .fontWeight(.bold) + .padding() + Text("Patagonia, founded in 1973 by Yvon Chouinard, emphasizes durable, repairable, and recyclable products, supporting a model that reduces waste and environmental impact.") + .foregroundStyle(Color(hex: "#2C4C52")) + .italic() + .font(.subheadline) + .padding(.horizontal) + .padding(.bottom) + + + + VStack { + Picker("Type", selection: $selectedType) { + Text("All").tag(ClothingType?.none) + ForEach(ClothingType.allCases, id: \.self) { type in + Text(type.rawValue).tag(type as ClothingType?) + } + } + .pickerStyle(.segmented) +// .background(Color(hex: "#2C4C52")) +// .clipShape(RoundedRectangle(cornerSize: CGSize(width: 7, height: 10))) + + Picker("Color", selection: $selectedColor) { + Text("All").tag(String?.none) + .foregroundStyle(Color(hex: "#2C4C52")) + Image(uiImage: ImageRenderer(content: Image(systemName: "circle.fill").foregroundStyle(.red)).uiImage!.withRenderingMode(.alwaysOriginal)) + .tag("Red" as String?) + Text("Blue").tag("Blue" as String?) + } + + } + .foregroundStyle(Color(hex: "#2C4C52")) + + .pickerStyle(.segmented) + + HStack { + Text("$0") + Slider(value: Binding(get: { + Double(maxPrice) + }, set: { newValue in + maxPrice = Int(newValue) + }), in: 0...500, step: 50) // Only allow integer values + .tint(Color(hex: "#2C4C52")) + + Text("$\(maxPrice)") + } + .foregroundStyle(Color(hex: "#2C4C52")) + .padding(.horizontal) + } + .padding(.horizontal) + + HStack { + Text("Shop") + .font(.title2) + .fontWeight(.bold) + Image("patagoniaFont") + .resizable() + .aspectRatio(contentMode: .fit) + .frame(width: 120, height: 30) + Spacer() + } + .padding(.horizontal) + + + + + LazyVGrid(columns: columns) { + ForEach(filteredItems) { clothingItem in + ClothCard(width: 160, height: 150, clothingItem: clothingItem) + } + } + Spacer() + } + .navigationTitle("Patagonia") + + } + } + + +#Preview { + aboutPatagoniaBrandView() +} diff --git a/Rethread/Rethread/sus1.mp4 b/Rethread/Rethread/sus1.mp4 new file mode 100644 index 0000000..c21d98d Binary files /dev/null and b/Rethread/Rethread/sus1.mp4 differ diff --git a/Rethread/Rethread/sus2.mp4 b/Rethread/Rethread/sus2.mp4 new file mode 100644 index 0000000..9538db4 Binary files /dev/null and b/Rethread/Rethread/sus2.mp4 differ diff --git a/Rethread/Rethread/sus3.mp4 b/Rethread/Rethread/sus3.mp4 new file mode 100644 index 0000000..db3ae84 Binary files /dev/null and b/Rethread/Rethread/sus3.mp4 differ