How to call SwiftUI NavigationLink conditionally?
Anyway it should be a button... something like
ScrollView(.vertical) {
ForEach(photos, id: \.self) { element in
Button(action: {
// here call a function with callback provided if password
// verification passed
self.checkPassword { verified in
if verified {
self.photo = element // store tapped element
self.isFired = true // << this might be called async
}
}
}) {
Image(uiImage: element.image)
}
}
}
.background(
// activate link for tapped photo
NavigationLink(destination: ImagePreviewView(photo: self.photo),
isActive: $isFired) { EmptyView() }
)
Change NavigationLink destination conditionally in SwiftUI
I assume you want to look at the element and to determine what view to show, the following achieves that. You can also use an enum for this.
The Collection
passes in the element, so you can use that and a conditional:
struct ProjectView: View {
var row: ItemsGroupModel
var body: some View {
Text("Project title = \(row.title)")
}
}
struct NonProjectView: View {
var row: ItemsGroupModel
var body: some View {
Text("Non-Project title = \(row.title)")
}
}
// row type of the collection view
struct ItemsGroupRow: View {
var data: ItemsGroupModel
var body: some View {
// This model is for one row
// I need to specify what view to open depending on what item of the collection view was selected (clicked on)
NavigationLink(destination: {
VStack{
if data.title.contains("project") {
ProjectView(row: data)
} else {
NonProjectView(row: data)
}
}
}()) { // open ProjectsView only if the user clicked on the item "Projects" of the list etc..
Text(data.title)
}
}
}
Note: I think the collection does have some bugs.
Example using enum
which does not work correctly:
import SwiftUI
struct ConditionalNavigationLinkView: View {
var body: some View {
GroupDetail()
}
}
// data displayed in the collection view
var itemsGroupData = [
ItemsGroupModel(.project), // should open ProjectsView()
ItemsGroupModel(.people), //should open PeopleView()
ItemsGroupModel(.agenda), //should open AgendaView()
ItemsGroupModel(.name) //should open NameView()
]
// main view where the collection view is shown
struct GroupDetail: View {
var body: some View {
NavigationView{
// FAMOUS COLLECTION ELEMENT
Collection(itemsGroupData, columns: 2, scrollIndicators: false) { row in
ItemsGroupRow(data: row)
}
}
}
}
enum ItemsGroupModelType: String {
case project = "Projects"
case people = "People"
case agenda = "Agenda"
case name = "Name"
}
// model of the data
struct ItemsGroupModel: Identifiable {
var id: UUID
let type: ItemsGroupModelType
init(_ type: ItemsGroupModelType) {
self.id = UUID()
self.type = type
}
}
struct ProjectView: View {
var row: ItemsGroupModel
var body: some View {
Text("Projects \(row.type.rawValue)")
}
}
struct NameView: View {
var row: ItemsGroupModel
var body: some View {
Text("NameView \(row.type.rawValue)")
}
}
struct PeopleView: View {
var row: ItemsGroupModel
var body: some View {
Text("PeopleView \(row.type.rawValue)")
}
}
struct AgendaView: View {
var row: ItemsGroupModel
var body: some View {
Text("AgendaView \(row.type.rawValue)")
}
}
// row type of the collection view
struct ItemsGroupRow: View {
func printingEmptyView() -> EmptyView {
print("type: \(data.type.rawValue)")
return EmptyView()
}
var data: ItemsGroupModel
var body: some View {
// This model is for one row
// I need to specify what view to open depending on what item of the collection view was selected (clicked on)
NavigationLink(destination: {
//print("Hello")
VStack{
self.printingEmptyView()
if data.type == .project {
ProjectView(row: data)
}
if data.type == .people {
PeopleView(row: data)
}
if data.type == .agenda {
AgendaView(row: data)
}
if data.type == .name {
NameView(row: data)
}
}
}()) { // open ProjectsView only if the user clicked on the item "Projects" of the list etc..
Text(data.type.rawValue)
}
}
}
How to put a condition to NavigationLink? SWIFTUI
Well, your question can be interpreted differently...
if you want to don't show the ability to go next until score is bigger that target at all, then it is
if score > target { // link will appear to user only when true
NavigationLink(destination: level2()) {
Text("Next Level")
}
}if you want to show link but don't allow to navigate until condition is true, then it is
NavigationLink(destination: level2()) {
Text("Next Level")
}.disabled(score <= target)if you want automatically navigate link when condition is true, then the possible variant is (but note - in such case you need manually manipulate back-forward navigation, or disallow back, etc.)
NavigationLink(destination: level2(), isActive: .constant(score > target)) {
Text("Next Level")
}
- alternate is to use explicit state for activation
How to navigate using button with condition check in SwiftUI
You can do something like this:
NavigationView {
VStack {
NavigationLink(destination: Dashboard(userName: self.userId, password: self.password), isActive: $showDashboard) {
Text("")
}
Button(action: {
if self.userId.isEmpty || self.password.isEmpty {
self.isAlert = true
} else {
self.showDashboard = true
}
}) {
Text("Submit")
.foregroundColor(.green)
.font(.system(size: 22))
}
}
}
A thing to remember is that a NavigationLink is a button itself and when pressed it navigate to the destinationView
, the isActive
parameter is a way to force that to happen (without the user clicking the NavigationLink). As of now I'm not sure how to embed logic into NavigationLinks.
Hope this helps :)
EDIT:
Another thing you can do is the following:
NavigationLink(destination:Dashboard(userName: self.userId, password: self.password)) {
Text("Submit")
}.disabled(self.userId.isEmpty || self.password.isEmpty )
This would disable the NavigationLink until both input fields are not empty.
Related Topics
Parse.Com Pfquery Order by Time (Swift)
Persist Accessibility Permissions Between Builds in Xcode 13
Background Thread Core Data Object Property Changes Doesn't Reflect on Ui
Downloading Firebase Storage Files Device Issue
What Are 3 Items in a Swift Method Parameter For
How to Define an Array of a Particular Enum Case in Swift
Firebase Datadescription Returns Empty Array
How to Give Xib Cell Button Action in Homevc in Swift
Why Does the Completion Handler Does Not Return Anything
Swift Optional Variable Assignment with Default Value (Double Question Marks)
Error: Couldn't Irgen Expression, No Additional Error
Uitextview Linktextattributes Font Attribute Not Applied to Nsattributedstring
What Does Cloning a Github Repository Mean
Apple Vision Framework - Text Extraction from Image
How to Correctly Initialize an Unsafepointer in Swift
Swiftui: Stop an Animation That Repeats Forever
Swift Package Manager Dynamic Library
Using Reflection to Set Object Properties Without Using Setvalue Forkey