Swiftpack.co - OrkhanAlikhanov/SwiftUIRouter as Swift Package

Swiftpack.co is a collection of thousands of indexed Swift packages. Search packages.
OrkhanAlikhanov/SwiftUIRouter
An experimental navigation router for SwiftUI
.package(url: "https://github.com/OrkhanAlikhanov/SwiftUIRouter.git", from: "1.0.0")

License

SwiftUIRouter 🔗

An ⚠️experimental⚠️ navigation router for SwiftUI

Usage

💡 Check out ExampleApp for more.

  1. Define your routes:
import SwiftUIRouter

extension NavigationRouteLink {
  static var login: NavigationRouteLink { "/login" }
  static var signUp: NavigationRouteLink { "/register" }
  
  static func userDetails(for user: User) -> NavigationRouteLink {
    NavigationRouteLink(path: "/users/\(user.id)", meta: [
      "user": user, /// can be used when resolving route link to a View. Check below how it's used.
    ])
  }
  
  static func userDetails(for id: Int) -> NavigationRouteLink {
    NavigationRouteLink(path: "/users/\(id)")
  }
}
  1. Implement how they should be resolved:
extension Array where Element == NavigationRoute {
  static var all: [NavigationRoute] {
    let login = NavigationRoute(path: "/login", destination: LoginPage())
    let register = NavigationRoute(path: "/register", destination: RegisterPage())
    let user = NavigationRoute(path: "/users/{id}") { route in
      /// meta "user" can passed when creating `NavigationRouteLink`. Eg. in `userDetails(for user: User)`
      /// Useful when you go to user details page and want to show user something until detailed data comes in.
      UserPage(user: route.meta("user") ?? User(id: route.int("id"), name: "Unknown"))
    }

    return [login, register, user]
  }
}
  1. Create root app:
struct ExampleApp: View {
  var body: some View {
    NavigationView {
      RouterView(router: .main, root: .login)
    }
    /// I don't know why, but setting \.router in RouterView itself was not enough. Probably NavigationView
    /// overrides environment of its children somehow. So we set \.router environment again
    .environment(\.router, .main)
    
    /// This is important because default one (DoubleColumnNavigationViewStyle) is
    /// updating NavigationLink.$isActive inconsistently causing navigation bugs.
    .navigationViewStyle(StackNavigationViewStyle())
  }
}

extension NavigationRouter {
  static var main = NavigationRouter(routes: .all)
}

Benefit:

struct LoginPage: View {
  @Environment(\.router) var router
  
  var body: some View {
    VStack {
      RouterLink(.signUp) { /// or use RouterLink("/register")
        Text("Don't have an acccount? Register here")
      }

      Button("Log in") {
        router.push(link: .userDetails(for: User(id: 1, name: "Orkhan")))
        // router.push(link: .userDetails(for: /* id */ 1)
      }
    }
    .navigationTitle("Login")
  }
}

Other works

  • LayoutSwift - Yet another Swift Autolayout DSL for iOS.
  • ChainSwift - ChainSwift 🔗 is an extension that provides chainable way of setting properties.

Installation

Swift Package Manager

Note: Instructions below are for using SwiftPM without the Xcode UI. It's the easiest to go to your Project Settings -> Swift Packages and add SwiftUIRouter from there.

To integrate using Apple's Swift Package Manager , without Xcode integration, add the following as a dependency to your Package.swift:

dependencies: [
  .package(url: "https://github.com/OrkhanAlikhanov/SwiftUIRouter.git", .upToNextMajor(from: "1.0.0"))
]

and then specify "SwiftUIRouter" as a dependency of the Target in which you wish to use SwiftUIRouter.

Manually

Just drag and drop the files in the Sources folder.

Authors

See also the list of contributors who participated in this project.

Love our work?

Hit the star 🌟 button! It helps! ❤️

License

This project is licensed under the MIT License - see the LICENSE file for details

GitHub

link
Stars: 10
Last commit: 16 weeks ago

Ad: Job Offers

iOS Software Engineer @ Perry Street Software
Perry Street Software is Jack’d and SCRUFF. We are two of the world’s largest gay, bi, trans and queer social dating apps on iOS and Android. Our brands reach more than 20 million members worldwide so members can connect, meet and express themselves on a platform that prioritizes privacy and security. We invest heavily into SwiftUI and using Swift Packages to modularize the codebase.

Submit a free job ad (while I'm testing this). The analytics numbers for this website are here.

Related Packages

Release Notes

v1.0.0
16 weeks ago

Swiftpack is being maintained by Petr Pavlik | @ptrpavlik | @swiftpackco | API | Analytics