diff --git a/WekoutThotViewer/WekoutThotViewer/ContentView.swift b/WekoutThotViewer/WekoutThotViewer/ContentView.swift index fd02e37..1a69de1 100644 --- a/WekoutThotViewer/WekoutThotViewer/ContentView.swift +++ b/WekoutThotViewer/WekoutThotViewer/ContentView.swift @@ -28,6 +28,7 @@ struct ContentView: View { } else { PlayerView(player: $avPlayer) .onAppear{ + avPlayer.isMuted = true avPlayer.play() } .onReceive(videoEnded){ _ in @@ -49,6 +50,7 @@ struct ContentView: View { func playVideo(url: String) { let url = URL(string: BaseURLs.currentBaseURL + url) avPlayer = AVPlayer(url: url!) + avPlayer.isMuted = true avPlayer.play() } diff --git a/iphone/Werkout_ios/APIModels/Workout.swift b/iphone/Werkout_ios/APIModels/Workout.swift index dccece6..2d88ac8 100644 --- a/iphone/Werkout_ios/APIModels/Workout.swift +++ b/iphone/Werkout_ios/APIModels/Workout.swift @@ -63,31 +63,51 @@ struct Workout: Codable, Identifiable, Equatable { } extension Array where Element == Workout { - func filterWorkouts(searchString: String, filteredRegisterdUser: RegisteredUser?) -> [Workout] { + func filterWorkouts(nameSearchString: String, + musclesSearchString: Set, + equipmentSearchString: Set, + filteredRegisterdUser: RegisteredUser?) -> [Workout] { var matchingWorkouts = [Workout]() - if (!searchString.isEmpty && searchString.count > 0) { + if matchingWorkouts.isEmpty { + matchingWorkouts.append(contentsOf: self) + } + + if (!nameSearchString.isEmpty && nameSearchString.count > 0) { matchingWorkouts = self.filter({ - if $0.name.lowercased().contains(searchString.lowercased()) { + if $0.name.lowercased().contains(nameSearchString.lowercased()) { return true } - - if let equipment = $0.equipment?.joined(separator: "").lowercased(), - equipment.contains(searchString.lowercased()) { - return true - } - - if let muscles = $0.muscles?.joined(separator: "").lowercased(), - muscles.contains(searchString.lowercased()) { - return true - } - return false }) } - if matchingWorkouts.isEmpty { - matchingWorkouts.append(contentsOf: self) + if (!equipmentSearchString.isEmpty && equipmentSearchString.count > 0) { + matchingWorkouts = matchingWorkouts.filter({ + if let equipment = $0.equipment?.joined(separator: "").lowercased() { + for word in equipmentSearchString { + if equipment.contains(word.lowercased()) { + return true + } + } + return false + } + return false + }) + } + + if (!musclesSearchString.isEmpty && musclesSearchString.count > 0) { + matchingWorkouts = matchingWorkouts.filter({ + if let muscles = $0.muscles?.joined(separator: "").lowercased() { + for word in musclesSearchString { + if muscles.contains(word.lowercased()) { + return true + } + } + return false + } + return false + }) } if let filteredRegisterdUser = filteredRegisterdUser { diff --git a/iphone/Werkout_ios/BaseURLs.swift b/iphone/Werkout_ios/BaseURLs.swift index 537f209..c43c8e6 100644 --- a/iphone/Werkout_ios/BaseURLs.swift +++ b/iphone/Werkout_ios/BaseURLs.swift @@ -12,6 +12,6 @@ enum BaseURLs: String { case dev = "https://dev.werkout.fitness" static var currentBaseURL: String { - return BaseURLs.local.rawValue + return BaseURLs.dev.rawValue } } diff --git a/iphone/Werkout_ios/Views/AllWorkouts/AllWorkoutsListView.swift b/iphone/Werkout_ios/Views/AllWorkouts/AllWorkoutsListView.swift index cb2c30e..2d6235e 100644 --- a/iphone/Werkout_ios/Views/AllWorkouts/AllWorkoutsListView.swift +++ b/iphone/Werkout_ios/Views/AllWorkouts/AllWorkoutsListView.swift @@ -9,11 +9,13 @@ import SwiftUI enum SortType: String, CaseIterable { case name = "Name" - case date = "Date" + case createdDate = "Created Date" } struct AllWorkoutsListView: View { - @State var searchString: String = "" + @State var searchNameString: String = "" + @State var selectedMuscles: Set = [] + @State var selectedEquipment: Set = [] @Binding var uniqueWorkoutUsers: [RegisteredUser]? @State private var filteredRegisterdUser: RegisteredUser? @@ -30,7 +32,9 @@ struct AllWorkoutsListView: View { Text((filteredRegisterdUser.firstName ?? "NA") + "'s Workouts") } - FilterAllView(searchString: $searchString, + FilterAllView(selectedMuscles: $selectedMuscles, + selectedEquipment: $selectedEquipment, + searchNameString: $searchNameString, uniqueWorkoutUsers: $uniqueWorkoutUsers, filteredRegisterdUser: $filteredRegisterdUser, filteredWorkouts: $filteredWorkouts, @@ -55,13 +59,28 @@ struct AllWorkoutsListView: View { refresh() } } - .onChange(of: searchString) { newValue in - filteredWorkouts = workouts.filterWorkouts(searchString: searchString, filteredRegisterdUser: filteredRegisterdUser) + .onChange(of: searchNameString) { newValue in + filterWorkouts() + } + .onChange(of: selectedMuscles) { newValue in + filterWorkouts() + } + .onChange(of: selectedEquipment) { newValue in + filterWorkouts() } .onAppear{ - filteredWorkouts = workouts.filterWorkouts(searchString: searchString, filteredRegisterdUser: filteredRegisterdUser) + filterWorkouts() } } + + func filterWorkouts() { + filteredWorkouts = workouts.filterWorkouts( + nameSearchString: searchNameString, + musclesSearchString: selectedMuscles, + equipmentSearchString: selectedEquipment, + filteredRegisterdUser: filteredRegisterdUser + ) + } } struct AllWorkoutsListView_Previews: PreviewProvider { diff --git a/iphone/Werkout_ios/Views/AllWorkouts/AllWorkoutsView.swift b/iphone/Werkout_ios/Views/AllWorkouts/AllWorkoutsView.swift index e1c48e8..df02a9d 100644 --- a/iphone/Werkout_ios/Views/AllWorkouts/AllWorkoutsView.swift +++ b/iphone/Werkout_ios/Views/AllWorkouts/AllWorkoutsView.swift @@ -155,7 +155,7 @@ struct AllWorkoutsView: View { healthStore.requestAuthorization(toShare: nil, read: healthKitTypes) { (succ, error) in if !succ { - fatalError("Error requesting authorization from health store: \(String(describing: error)))") +// fatalError("Error requesting authorization from health store: \(String(describing: error)))") } } } diff --git a/iphone/Werkout_ios/Views/CompletedWorkout/CompletedWorkoutView.swift b/iphone/Werkout_ios/Views/CompletedWorkout/CompletedWorkoutView.swift index d8cefcb..5f7589e 100644 --- a/iphone/Werkout_ios/Views/CompletedWorkout/CompletedWorkoutView.swift +++ b/iphone/Werkout_ios/Views/CompletedWorkout/CompletedWorkoutView.swift @@ -76,19 +76,19 @@ struct CompletedWorkoutView: View { .onAppear{ bridgeModule.sendWorkoutCompleteToWatch() } - .onChange(of: bridgeModule.healthKitUUID, perform: { healthKitUUID in - if let healthKitUUID = healthKitUUID { - gettingHealthKitData = true - healthKitHelper.getDetails(forHealthKitUUID: healthKitUUID, - completion: { healthKitWorkoutData in - guard let healthStore = healthKitWorkoutData else { - return - } - self.healthKitWorkoutData = healthKitWorkoutData - gettingHealthKitData = false - }) - } - }) +// .onChange(of: bridgeModule.healthKitUUID, perform: { healthKitUUID in +// if let healthKitUUID = healthKitUUID { +// gettingHealthKitData = true +// healthKitHelper.getDetails(forHealthKitUUID: healthKitUUID, +// completion: { healthKitWorkoutData in +// guard let healthStore = healthKitWorkoutData else { +// return +// } +// self.healthKitWorkoutData = healthKitWorkoutData +// gettingHealthKitData = false +// }) +// } +// }) } func upload(postBody: [String: Any]) { diff --git a/iphone/Werkout_ios/Views/CreateWorkout/CreateExerciseActionsView.swift b/iphone/Werkout_ios/Views/CreateWorkout/CreateExerciseActionsView.swift index 0f6dfa7..23e76e6 100644 --- a/iphone/Werkout_ios/Views/CreateWorkout/CreateExerciseActionsView.swift +++ b/iphone/Werkout_ios/Views/CreateWorkout/CreateExerciseActionsView.swift @@ -89,8 +89,6 @@ struct CreateExerciseActionsView: View { Spacer() } - - Divider() } } } diff --git a/iphone/Werkout_ios/Views/ExternalWorkoutDetailView.swift b/iphone/Werkout_ios/Views/ExternalWorkoutDetailView.swift index 42af69a..643588a 100644 --- a/iphone/Werkout_ios/Views/ExternalWorkoutDetailView.swift +++ b/iphone/Werkout_ios/Views/ExternalWorkoutDetailView.swift @@ -26,6 +26,7 @@ struct ExternalWorkoutDetailView: View { PlayerView(player: $avPlayer) .frame(width: metrics.size.width * 0.5, height: metrics.size.height * 0.8) .onAppear{ + avPlayer.isMuted = true avPlayer.play() } } @@ -48,6 +49,7 @@ struct ExternalWorkoutDetailView: View { .frame(width: metrics.size.width * 0.2, height: metrics.size.height * 0.2) .onAppear{ + avPlayer.isMuted = true avPlayer.play() } } diff --git a/iphone/Werkout_ios/Views/WorkoutDetail/ExerciseListView.swift b/iphone/Werkout_ios/Views/WorkoutDetail/ExerciseListView.swift index 3619914..af44fbb 100644 --- a/iphone/Werkout_ios/Views/WorkoutDetail/ExerciseListView.swift +++ b/iphone/Werkout_ios/Views/WorkoutDetail/ExerciseListView.swift @@ -25,6 +25,7 @@ struct ExerciseListView: View { exerciseName: self.videoExercise?.name, workout: bridgeModule.currentWorkoutInfo.workout) { avPlayer = AVPlayer(url: videoURL) + avPlayer.isMuted = true avPlayer.play() } } @@ -137,6 +138,7 @@ struct ExerciseListView: View { .sheet(item: $videoExercise) { exercise in PlayerView(player: $avPlayer) .onAppear{ + avPlayer.isMuted = true avPlayer.play() } } diff --git a/iphone/Werkout_ios/Views/WorkoutDetail/WorkoutDetailView.swift b/iphone/Werkout_ios/Views/WorkoutDetail/WorkoutDetailView.swift index 0596796..a72a301 100644 --- a/iphone/Werkout_ios/Views/WorkoutDetail/WorkoutDetailView.swift +++ b/iphone/Werkout_ios/Views/WorkoutDetail/WorkoutDetailView.swift @@ -46,6 +46,7 @@ struct WorkoutDetailView: View { PlayerView(player: $avPlayer) .frame(width: metrics.size.width * 1, height: metrics.size.height * 1) .onAppear{ + avPlayer.isMuted = true avPlayer.play() } @@ -59,6 +60,7 @@ struct WorkoutDetailView: View { exerciseName: currentExtercise.exercise.name, workout: bridgeModule.currentWorkoutInfo.workout) { avPlayer = AVPlayer(url: otherVideoURL) + avPlayer.isMuted = true avPlayer.play() } }, label: { @@ -169,6 +171,7 @@ struct WorkoutDetailView: View { exerciseName: currentExtercise.exercise.name, workout: bridgeModule.currentWorkoutInfo.workout) { avPlayer = AVPlayer(url: videoURL) + avPlayer.isMuted = true avPlayer.play() } } @@ -181,6 +184,7 @@ struct WorkoutDetailView: View { } .onReceive(NotificationCenter.default.publisher( for: UIScene.willEnterForegroundNotification)) { _ in + avPlayer.isMuted = true avPlayer.play() } } @@ -194,6 +198,7 @@ struct WorkoutDetailView: View { exerciseName: currentExtercise.exercise.name, workout: bridgeModule.currentWorkoutInfo.workout) { avPlayer = AVPlayer(url: videoURL) + avPlayer.isMuted = true avPlayer.play() } } diff --git a/iphone/Werkout_ios/subview/AddSupersetView.swift b/iphone/Werkout_ios/subview/AddSupersetView.swift index 1552116..d235e73 100644 --- a/iphone/Werkout_ios/subview/AddSupersetView.swift +++ b/iphone/Werkout_ios/subview/AddSupersetView.swift @@ -12,25 +12,34 @@ struct AddSupersetView: View { @Binding var selectedCreateWorkoutSuperSet: CreateWorkoutSuperSet? var body: some View { - VStack { + TabView { ForEach(createWorkoutSuperSet.exercises, id: \.id) { createWorkoutExercise in - HStack { - VStack { - Text(createWorkoutExercise.exercise.name) - .font(.title2) - .frame(maxWidth: .infinity) - if createWorkoutExercise.exercise.side != nil && createWorkoutExercise.exercise.side!.count > 0 { - Text(createWorkoutExercise.exercise.side!) - .font(.title3) - .frame(maxWidth: .infinity, alignment: .center) - } - CreateExerciseActionsView(workoutExercise: createWorkoutExercise, - superset: createWorkoutSuperSet, - viewModel: viewModel) - + VStack { + Text(createWorkoutExercise.exercise.name) + .font(.title2) + .frame(maxWidth: .infinity) + if createWorkoutExercise.exercise.side != nil && createWorkoutExercise.exercise.side!.count > 0 { + Text(createWorkoutExercise.exercise.side!) + .font(.title3) + .frame(maxWidth: .infinity, alignment: .center) } + CreateExerciseActionsView(workoutExercise: createWorkoutExercise, + superset: createWorkoutSuperSet, + viewModel: viewModel) } + .frame(width: 300.0) + .padding(.bottom, 40) } } + .frame(height: 300) + .tabViewStyle(.page) + .onAppear { + setupAppearance() + } + } + + func setupAppearance() { + UIPageControl.appearance().currentPageIndicatorTintColor = .black + UIPageControl.appearance().pageIndicatorTintColor = UIColor.black.withAlphaComponent(0.2) } } diff --git a/iphone/Werkout_ios/subview/AllExerciseView.swift b/iphone/Werkout_ios/subview/AllExerciseView.swift index 50195a7..36f8f34 100644 --- a/iphone/Werkout_ios/subview/AllExerciseView.swift +++ b/iphone/Werkout_ios/subview/AllExerciseView.swift @@ -82,6 +82,7 @@ struct AllExerciseView: View { .sheet(item: $videoExercise) { exercise in PlayerView(player: $avPlayer) .onAppear{ + avPlayer.isMuted = true avPlayer.play() } } diff --git a/iphone/Werkout_ios/subview/FilterAllView.swift b/iphone/Werkout_ios/subview/FilterAllView.swift index 09a0b59..448c7bf 100644 --- a/iphone/Werkout_ios/subview/FilterAllView.swift +++ b/iphone/Werkout_ios/subview/FilterAllView.swift @@ -8,7 +8,9 @@ import SwiftUI struct FilterAllView: View { - @Binding var searchString: String + @Binding var selectedMuscles: Set + @Binding var selectedEquipment: Set + @Binding var searchNameString: String @Binding var uniqueWorkoutUsers: [RegisteredUser]? @Binding var filteredRegisterdUser: RegisteredUser? @Binding var filteredWorkouts: [Workout] @@ -16,48 +18,113 @@ struct FilterAllView: View { @Binding var currentSort: SortType? var body: some View { - HStack { - TextField("Filter" ,text: $searchString) + VStack { + TextField("Search by name" ,text: $searchNameString) .padding(.horizontal) .textFieldStyle(.roundedBorder) - - if let uniqueWorkoutUsers = uniqueWorkoutUsers { - Menu(content: { - ForEach(uniqueWorkoutUsers, id: \.self) { index in + + HStack { + if let uniqueWorkoutUsers = uniqueWorkoutUsers { + Menu(content: { + ForEach(uniqueWorkoutUsers, id: \.self) { index in + Button(action: { + filteredRegisterdUser = index + filteredWorkouts = workouts.filterWorkouts( + nameSearchString: searchNameString, + musclesSearchString: selectedMuscles, + equipmentSearchString: selectedEquipment, + filteredRegisterdUser: filteredRegisterdUser + ) + }, label: { + Text((index.firstName ?? "") + " -" + (index.lastName ?? "")) + }) + } + Button(action: { - filteredRegisterdUser = index - filteredWorkouts = workouts.filterWorkouts(searchString: searchString, - filteredRegisterdUser: filteredRegisterdUser) + filteredRegisterdUser = nil + filteredWorkouts = workouts.filterWorkouts( + nameSearchString: searchNameString, + musclesSearchString: selectedMuscles, + equipmentSearchString: selectedEquipment, + filteredRegisterdUser: filteredRegisterdUser + ) }, label: { - Text((index.firstName ?? "") + " -" + (index.lastName ?? "")) + Text("All") + }) + + }, label: { + Image(systemName: filteredRegisterdUser == nil ? "person.2" : "person.2.fill") + .padding(.trailing) + }) + } + + Menu(content: { + ForEach(SortType.allCases, id: \.self) { index in + Button(action: { + sortWorkouts(sortType: index) + }, label: { + Text(index.rawValue) }) } - - Button(action: { - filteredRegisterdUser = nil - filteredWorkouts = workouts.filterWorkouts(searchString: searchString,filteredRegisterdUser: filteredRegisterdUser) - }, label: { - Text("All") - }) - }, label: { - Image(systemName: filteredRegisterdUser == nil ? "person.2" : "person.2.fill") + Image(systemName: "list.number") + .padding(.trailing) + }) + + if let equipments = DataStore.shared.allEquipment { + Menu(content: { + ForEach(equipments, id: \.id) { equipment in + Button(action: { + if selectedEquipment.contains(equipment.name) { + selectedEquipment.remove(equipment.name) + } else { + selectedEquipment.insert(equipment.name) + } + }, label: { + if selectedEquipment.contains(equipment.name) { + Image(systemName: "checkmark") + } + Text(equipment.name) + }) + } + }, label: { + Image(systemName: "scalemass") + .padding(.trailing) + }) + } + + if let muscles = DataStore.shared.allMuscles { + Menu(content: { + ForEach(muscles, id: \.id) { muscle in + Button(action: { + if selectedMuscles.contains(muscle.name) { + selectedMuscles.remove(muscle.name) + } else { + selectedMuscles.insert(muscle.name) + } + }, label: { + if selectedMuscles.contains(muscle.name) { + Image(systemName: "checkmark") + } + Text(muscle.name) + }) + } + }, label: { + Image(systemName: "brain.head.profile") + .padding(.trailing) + }) + } + + Button(action: { + selectedMuscles.removeAll() + selectedEquipment.removeAll() + searchNameString = "" + filteredRegisterdUser = nil + }, label: { + Image(systemName: "xmark.circle") .padding(.trailing) }) } - - Menu(content: { - ForEach(SortType.allCases, id: \.self) { index in - Button(action: { - sortWorkouts(sortType: index) - }, label: { - Text(index.rawValue) - }) - } - }, label: { - Image(systemName: "list.number") - .padding(.trailing) - }) } } @@ -71,7 +138,7 @@ struct FilterAllView: View { filteredWorkouts = filteredWorkouts.sorted(by: { $0.name < $1.name }) - case .date: + case .createdDate: filteredWorkouts = filteredWorkouts.sorted(by: { $0.createdAt ?? Date() < $1.createdAt ?? Date() }) @@ -81,7 +148,9 @@ struct FilterAllView: View { } #Preview { - FilterAllView(searchString: .constant(""), + FilterAllView(selectedMuscles: .constant([]), + selectedEquipment: .constant([]), + searchNameString: .constant(""), uniqueWorkoutUsers: .constant(nil), filteredRegisterdUser: .constant(nil), filteredWorkouts: .constant(PreviewData.allWorkouts()), diff --git a/iphone/Werkout_ios/subview/PlannedWorkoutView.swift b/iphone/Werkout_ios/subview/PlannedWorkoutView.swift index 2435c3f..33cbe4b 100644 --- a/iphone/Werkout_ios/subview/PlannedWorkoutView.swift +++ b/iphone/Werkout_ios/subview/PlannedWorkoutView.swift @@ -13,7 +13,7 @@ struct PlannedWorkoutView: View { var body: some View { List { - ForEach(workouts, id:\.workout.name) { plannedWorkout in + ForEach(workouts.sorted(by: { $0.onDate < $1.onDate }), id:\.workout.name) { plannedWorkout in HStack { VStack(alignment: .leading) { Text(plannedWorkout.onDate.plannedDate?.weekDay ?? "-") diff --git a/iphone/Werkout_ios/subview/PlayerUIView.swift b/iphone/Werkout_ios/subview/PlayerUIView.swift index 8df8813..4ff5602 100644 --- a/iphone/Werkout_ios/subview/PlayerUIView.swift +++ b/iphone/Werkout_ios/subview/PlayerUIView.swift @@ -62,6 +62,7 @@ class PlayerUIView: UIView { if let playerItem = notification.object as? AVPlayerItem { playerItem.seek(to: .zero, completionHandler: nil) self.playerLayer.player?.play() + self.playerLayer.player?.isMuted = true } } }