At first, we need to get default navigationBar height to bind the right view size with the height to avoid hard-coding.
Step 1: get navigationBar height
NavigationConfiguration.swift
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | struct NavigationConfiguration : UIViewControllerRepresentable { var config : ( UINavigationController ) - > Void = { _ in } func makeUIViewController ( context : Context ) - > some UIViewController { let controller = UIViewController () DispatchQueue . main . async { if let nc = controller . navigationController { self . config ( nc ) } } return controller } func updateUIViewController ( _ uiViewController : UIViewControllerType , context : Context ) { if let nc = uiViewController . navigationController { self . config ( nc ) } } } |
GetDefaultNavBarHeightView.swift
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | struct GetDefaultNavBarHeightView : View { @Binding var defaultNavHeight : CGFloat @State var isHidden : Bool = false var body : some View { if ! isHidden { Text ( "" ) . background ( NavigationConfiguration ( config : { ( nc ) in self . defaultNavHeight = nc . navigationBar . frame . height }) ) } } } |
Step 2: build customize right view
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 | struct NavRightView : View { var defaultNavHeight : CGFloat init ( defaultNavHeight : CGFloat ) { self . defaultNavHeight = defaultNavHeight } var body : some View { HStack { NavigationLink ( destination : Text ( "material" )) { NavRightUnitView ( imgName : "material" , des : "资料圈" , defaultNavHeight : self . defaultNavHeight ) } Spacer () NavigationLink ( destination : Text ( "group" )) { NavRightUnitView ( imgName : "group" , des : "备考群" , defaultNavHeight : self . defaultNavHeight ) } } } } struct NavRightUnitView : View { var defaultNavHeight : CGFloat var imgName : String var des : String init ( imgName : String , des : String , defaultNavHeight : CGFloat ) { self . imgName = imgName self . des = des self . defaultNavHeight = defaultNavHeight } var body : some View { VStack { Image ( imgName ) . resizable () . aspectRatio ( contentMode : . fit ) . frame ( width : 0.55 * self . defaultNavHeight , height : 0.55 * self . defaultNavHeight , alignment : . center ) Text ( des ) . font (. system ( size : 0.25 * self . defaultNavHeight )) . foregroundColor (. black ) } } } |
ContentView.swift
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | struct ContentView : View { @State var defaultNavHeight : CGFloat = 0 var body : some View { NavigationView { ZStack { GetDefaultNavBarHeightView ( defaultNavHeight : $ defaultNavHeight ) Text ( "good" ) } . navigationBarTitleDisplayMode (. inline ) . navigationBarItems ( trailing : NavRightView ( defaultNavHeight : defaultNavHeight )) } } } |