I'll just drop the entire view for you. This is a user account view, with a sheet to change their password. As I mentioned, the goal here is to dismiss the "change password sheet" once the @Published property switches to True from my class.
I think ultimately what doesn't make sense is how I "listen" to the @Published property while at the same time bind to the local @State properties in my view that manage the sheet as well.
Ignore all the Account Image stuff.
struct SLPAccountProfileView: View {
let slpAccountProfilePicVM = SLPAccountProfilePicture()
@StateObject var slpAccountVM = SLPChangeAccountPassword()
private let userAccountProperties = SLPDataManager.shared.returnUsersProfileDetails()
@State private var passwordChangeTapped = false
@State var selectedImage: UIImage?
@State var profileImage: Image?
@State var imagePickerPresented = false
var body: some View {
NavigationView {
VStack {
if profileImage == nil {
Button(action: { imagePickerPresented = true }, label: {
Image("ProfilePlaceholder")
.clipShape(Circle())
.frame(width: 72, height: 72)
})
.sheet(isPresented: $imagePickerPresented, onDismiss: loadImageFirstTime, content: {
ImagePicker(image: $selectedImage)
})
} else if let image = profileImage {
VStack {
Button(action: { imagePickerPresented = true }, label: {
image
.resizable()
.scaledToFill()
.clipped()
.clipShape(Circle())
.frame(width: 72, height: 72)
})
.sheet(isPresented: $imagePickerPresented, onDismiss: loadNewImage, content: {
ImagePicker(image: $selectedImage)
})
}
}
VStack {
List {
Section(header: Text("Name")){
SLPAccountListItems(item: "\(userAccountProperties?.first_name ?? "empty")" + " \(userAccountProperties?.last_name ?? "empty")")
}
.font(.custom("Poppins", size: 12))
.foregroundColor(Color(#colorLiteral(red: 0.9803921569, green: 0.6784313725, blue: 0.2823529412, alpha: 1)))
Section(header: Text("Email")){
SLPAccountListItems(item: userAccountProperties?.email ?? "empty")
}
.font(.custom("Poppins", size: 12))
.foregroundColor(Color(#colorLiteral(red: 0.9803921569, green: 0.6784313725, blue: 0.2823529412, alpha: 1)))
Section(header: Text("Phone Number")) {
SLPAccountListItems(item: userAccountProperties?.mobile_number ?? "empty")
}
.font(.custom("Poppins", size: 12))
.foregroundColor(Color(#colorLiteral(red: 0.9803921569, green: 0.6784313725, blue: 0.2823529412, alpha: 1)))
Section(header: Text("Timezone")) {
SLPAccountListItems(item: userAccountProperties?.timezone ?? "empty")
}
.font(.custom("Poppins", size: 12))
.foregroundColor(Color(#colorLiteral(red: 0.9803921569, green: 0.6784313725, blue: 0.2823529412, alpha: 1)))
}
.listStyle(GroupedListStyle())
Button(action: { SLPDataManager.shared.logOut() }, label: {
Text("Log Out")
.font(.custom("Poppins", size: 18))
.fontWeight(.medium)
.foregroundColor(Color(#colorLiteral(red: 1, green: 1, blue: 1, alpha: 1)))
.frame(width: 200, height: 50)
.background(Color(#colorLiteral(red: 0.1521442533, green: 0.4429811835, blue: 0.6690705419, alpha: 1)))
.cornerRadius(10)
.overlay(
RoundedRectangle(cornerRadius: 8)
.stroke(Color(#colorLiteral(red: 0.9803921569, green: 0.6784313725, blue: 0.2823529412, alpha: 1)), lineWidth: 1.3)
)
})
.padding(2)
Button(action: { passwordChangeTapped = true }, label: {
Text("Change password")
.font(.custom("Poppins", size: 22))
.fontWeight(.regular)
.foregroundColor(Color(#colorLiteral(red: 0.9803921569, green: 0.6784313725, blue: 0.2823529412, alpha: 1)))
})
.padding(.bottom, 60)
.padding(.top, 10)
}
}
.navigationViewStyle(StackNavigationViewStyle())
.navigationBarHidden(true)
.sheet(isPresented: $passwordChangeTapped, content: {
PasswordChangeView(showSheetPresented: $passwordChangeTapped)
})
}
}
}
struct PasswordChangeView: View {
@StateObject var slpAccountVM = SLPChangeAccountPassword()
@Binding var showSheetPresented: Bool
var body: some View {
NavigationView {
VStack {
Text("Change password")
.headline1TextStyle()
.padding(.bottom, 20)
VStack {
HStack {
Image(systemName: "number")
.font(.system(size: 27, weight: .ultraLight))
.foregroundColor(slpAccountVM.isOldPasswordValid() ? .green : .black)
SecureField("Current password", text: $slpAccountVM.oldPassword)
.modifier(TextFieldStyle())
}
.padding(.bottom, 10)
HStack {
Image(systemName: "number")
.font(.system(size: 27, weight: .ultraLight))
.foregroundColor(slpAccountVM.isNewPasswordValid() ? .green : .black)
SecureField("New password", text: $slpAccountVM.newPassword)
.modifier(TextFieldStyle())
}
.padding(.bottom, 10)
// Text("You will be logged out after changing your password")
// .font(.custom("Poppins", size: 14))
// .fontWeight(.medium)
// .foregroundColor(.gray)
// .frame(maxWidth: 300, alignment: .center)
}
Spacer()
if slpAccountVM.passwordFormVerified {
Button(action: { slpAccountVM.changeSlpUserPassword() }, label: {
ActivityIndicator(isAnimating: slpAccountVM.isSending)
Text(slpAccountVM.isSending ? "Submitting..." : "Submit")
.font(.custom("Poppins", size: 18))
.fontWeight(.medium)
.foregroundColor(Color(#colorLiteral(red: 1, green: 1, blue: 1, alpha: 1)))
.frame(width: 200, height: 50)
.background(Color(#colorLiteral(red: 0.1521442533, green: 0.4429811835, blue: 0.6690705419, alpha: 1)))
.cornerRadius(10)
.overlay(
RoundedRectangle(cornerRadius: 8)
.stroke(Color(#colorLiteral(red: 0.9803921569, green: 0.6784313725, blue: 0.2823529412, alpha: 1)), lineWidth: 1.3)
)
})
}
if slpAccountVM.passwordChangeFailedAfter == true {
Text("Something went wrong while trying to change your password. Please contact support if you continue to experience problems")
.font(.custom("Poppins", size: 14))
.fontWeight(.medium)
.foregroundColor(.red)
.frame(maxWidth: 300, alignment: .center)
}
}
.navigationBarItems(trailing: Button(action: {
showSheetPresented.toggle()
}, label: {
Text("Cancel")
}))
}
}
}