A declarative routing and navigation framework for SwiftUI apps
Tip1: This is a experimental framework. You should be careful about production use.
Tip2: NavigationStack
for iOS16+ is much more better than NavigationView
. It is recommended to try out NavigationStack
before using SwiftUINavigator in iOS16+ project.
SwiftUI is a great declarative UI framework, but NavigationView
is a imperative navigation framework. With NavigationView
, source page should build complete destination view for navigation. This results in bad coupling. And NavigationView
don't have enough API to do custom navigation, it's not easy to develop a middle/big app with NavigationView
.
So I design the SwiftUINavigator
to provide a declarative routing framework which is more suitable with SwiftUI and has better navigation ability.
But because of the limitation of SwiftUI, SwiftUINavigator
use ZStack
to realize a custom Navigation Stack. I'm not sure if it's reliable enough for all apps.
Examples to show how to use SwiftUINavigator
First, declare all routes.
@main
struct CaseStudyApp: App {
var body: some Scene {
WindowGroup {
Router(initialName: HomeSceneName) {
NavScene(HomeSceneName) {
HomeScene()
}
NavScene(NavActionSceneName) { properties in
let tagStr = properties["tag"] ?? "0"
NavActionScene(tag: Int(tagStr) ?? 0)
}
NavScene(FadeSceneName) {
FadeScene()
}.fadeTransition()
NavScene(PopupSceneName) {
PopupScene()
}
NavScene("*") {
UnknownScene()
}
}
}
}
}
Then write your scenes. There are 3 EnvironmentObject you can achieve in scene:
let NavActionSceneName = "nav_action"
struct NavActionScene: View {
@EnvironmentObject private var navigator: Navigator
@EnvironmentObject private var navigationState : NavigationState
@EnvironmentObject private var sceneState : NavigateSceneState
var tag : Int = 0
var body: some View {
var fullPath = ""
for sceneState in navigationState.historyStack {
fullPath += "/\(sceneState.sceneName)"
}
return VStack() {
NavBar(title: "NavAction-\(tag)")
Text("currentFullPath: \(fullPath)")
Button("push") {
navigator.push(NavActionSceneName,properties: ["tag": String(tag + 1)])
}
Button("present") {
navigator.present(NavActionSceneName,properties: ["tag": String(tag + 1)])
}
Button("replace") {
navigator.replace(NavActionSceneName,properties: ["tag": String(tag + 1)])
}
Button("backToHome") {
navigator.goBack(total: .max, animated: true)
}
Spacer()
}.background(sceneState.navigationType == .Push ? .white : .gray)
.offset(x: 0, y: sceneState.navigationType == .Push ? 0 : 150)
}
}
Detail usage -> Examples
You can add SwiftUINavigator to an Xcode project by adding it as a package dependency.
Issues and PRs are warmly welcome.
Contact me by email([email protected])
link |
Stars: 2 |
Last commit: 1 year ago |
fix ci
Swiftpack is being maintained by Petr Pavlik | @ptrpavlik | @swiftpackco | API | Analytics