Tuesday, February 7, 2023
Learning Code
  • Home
  • JavaScript
  • Java
  • Python
  • Swift
  • C++
  • C#
No Result
View All Result
  • Home
  • JavaScript
  • Java
  • Python
  • Swift
  • C++
  • C#
No Result
View All Result
Learning Code
No Result
View All Result
Home Swift

A Beginner’s Guide to NavigationSplitView in SwiftUI for iOS 16

learningcode_x1mckf by learningcode_x1mckf
September 4, 2022
in Swift
0
A Beginner’s Guide to NavigationSplitView in SwiftUI for iOS 16
74
SHARES
1.2k
VIEWS
Share on FacebookShare on Twitter


In iOS 16, apart from introducing the brand new NavigationStack, Apple additionally launched a brand new view container named NavigationSplitView for builders to create two or three column navigation interface. If you wish to construct UI just like the inventory Mail app, you need to try this cut up view part.

You might also like

The abstract Vapor service factory design pattern

SwiftNIO tutorial – The echo server

Introducing – Vapor cheatsheet – The.Swift.Dev.

Whereas NavigationSplitView is extra appropriate for iPadOS and macOS apps, it’s also possible to apply it to apps for iPhone. The view part mechanically adapts itself for iPhone. As a substitute of displaying a multi-column interface, it creates a single-column expertise.

The brand new NavigationSplitView comes with varied choices so that you can customise its look and operations. You may change the column width and programmatically present/disguise the columns.

On this tutorial, we are going to create a three-column navigation UI utilizing NavigationSplitView.

Let’s get began.

The Fundamental Utilization of NavigationSplitView

The NavigationSplitView helps each two-column and three-column navigation expertise. Their implementations are fairly related. To create a two-column navigation UI, you write the code like this:

NavigationSplitView {

  // Menu bar

} element: {

  // Element view for every of the menu merchandise

}

For 3-column navigation interface, you add the content material parameter in between:

NavigationSplitView {

  // Menu bar

} content material: {

  // Sub menu

} element: {

  // Element view for every of the sub-menu merchandise

}

We’ll begin with the two-column navigation UI and finally construct the three-column design.

Constructing the 2-Column Navigation Interface

In case you’ve learn my earlier tutorial on the expandable listing view, you might know that I’m an enormous fan of La Marzocco. In that tutorial, I confirmed you how one can create an expandable listing view with inset group type.

Now let’s flip this expandable listing right into a two stage navigation interface just like the screenshot proven beneath:

swiftui-navigationsplitview-two-column

Earlier than we create the cut up view, let’s start with the info mannequin. We create a struct to mannequin a menu merchandise:

struct MenuItem: Identifiable, Hashable {

    var id = UUID()

    var title: String

    var picture: String

    var subMenuItems: [MenuItem]?

}

To make a nested listing, the important thing right here is to incorporate a property that incorporates an non-obligatory array of youngsters (i.e. subMenuItems). Be aware that the youngsters are of the identical kind of its guardian.

For the highest stage menu gadgets, we are able to create an array of MenuItem like this:

let topMenuItems = [ MenuItem(name: “Espresso Machines”, image: “linea-mini”, subMenuItems: espressoMachineMenuItems),

                        MenuItem(name: “Grinders”, image: “swift-mini”, subMenuItems: grinderMenuItems),

                        MenuItem(name: “Other Equipments”, image: “espresso-ep”, subMenuItems: otherMenuItems)

                    ]

For every of the menu merchandise, we specify the array of the sub-menu gadgets. In case if there isn’t any sub-menu merchandise, you possibly can omit the subMenuItems parameter or go it a nil worth. For the sub-menu gadgets, we are able to outline them like this:

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

// Sub-menu gadgets for Espressco Machines

let espressoMachineMenuItems = [ MenuItem(name: “Leva”, image: “leva-x”, subMenuItems: [ MenuItem(name: “Leva X”, image: “leva-x”), MenuItem(name: “Leva S”, image: “leva-s”) ]),

                                 MenuItem(title: “Strada”, picture: “strada-ep”, subMenuItems: [ MenuItem(name: “Strada EP”, image: “strada-ep”), MenuItem(name: “Strada AV”, image: “strada-av”), MenuItem(name: “Strada MP”, image: “strada-mp”), MenuItem(name: “Strada EE”, image: “strada-ee”) ]),

                                 MenuItem(title: “KB90”, picture: “kb90”),

                                 MenuItem(title: “Linea”, picture: “linea-pb-x”, subMenuItems: [ MenuItem(name: “Linea PB X”, image: “linea-pb-x”), MenuItem(name: “Linea PB”, image: “linea-pb”), MenuItem(name: “Linea Classic”, image: “linea-classic”) ]),

                                 MenuItem(title: “GB5”, picture: “gb5”),

                                 MenuItem(title: “Dwelling”, picture: “gs3”, subMenuItems: [ MenuItem(name: “GS3”, image: “gs3”), MenuItem(name: “Linea Mini”, image: “linea-mini”) ])

                                ]

 

// Sub-menu gadgets for Grinder

let grinderMenuItems = [ MenuItem(name: “Swift”, image: “swift”),

                         MenuItem(name: “Vulcano”, image: “vulcano”),

                         MenuItem(name: “Swift Mini”, image: “swift-mini”),

                         MenuItem(name: “Lux D”, image: “lux-d”)

                        ]

 

// Sub-menu gadgets for different tools

let otherMenuItems = [ MenuItem(name: “Espresso AV”, image: “espresso-av”),

                         MenuItem(name: “Espresso EP”, image: “espresso-ep”),

                         MenuItem(name: “Pour Over”, image: “pourover”),

                         MenuItem(name: “Steam”, image: “steam”)

                        ]

To higher manage the info mannequin, we create a struct referred to as CoffeeEquipmentModel like this:

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

49

50

51

52

53

54

55

struct CoffeeEquipmenModel {

    let mainMenuItems = {

        // High menu gadgets

        let topMenuItems = [ MenuItem(name: “Espresso Machines”, image: “linea-mini”, subMenuItems: espressoMachineMenuItems),

                                MenuItem(name: “Grinders”, image: “swift-mini”, subMenuItems: grinderMenuItems),

                                MenuItem(name: “Other Equipments”, image: “espresso-ep”, subMenuItems: otherMenuItems)

                            ]

 

        // Sub-menu gadgets for Espresso Machines

        let espressoMachineMenuItems = [ MenuItem(name: “Leva”, image: “leva-x”, subMenuItems: [ MenuItem(name: “Leva X”, image: “leva-x”), MenuItem(name: “Leva S”, image: “leva-s”) ]),

                                         MenuItem(title: “Strada”, picture: “strada-ep”, subMenuItems: [ MenuItem(name: “Strada EP”, image: “strada-ep”), MenuItem(name: “Strada AV”, image: “strada-av”), MenuItem(name: “Strada MP”, image: “strada-mp”), MenuItem(name: “Strada EE”, image: “strada-ee”) ]),

                                         MenuItem(title: “KB90”, picture: “kb90”),

                                         MenuItem(title: “Linea”, picture: “linea-pb-x”, subMenuItems: [ MenuItem(name: “Linea PB X”, image: “linea-pb-x”), MenuItem(name: “Linea PB”, image: “linea-pb”), MenuItem(name: “Linea Classic”, image: “linea-classic”) ]),

                                         MenuItem(title: “GB5”, picture: “gb5”),

                                         MenuItem(title: “Dwelling”, picture: “gs3”, subMenuItems: [ MenuItem(name: “GS3”, image: “gs3”), MenuItem(name: “Linea Mini”, image: “linea-mini”) ])

                                        ]

 

        // Sub-menu gadgets for Grinder

        let grinderMenuItems = [ MenuItem(name: “Swift”, image: “swift”),

                                 MenuItem(name: “Vulcano”, image: “vulcano”),

                                 MenuItem(name: “Swift Mini”, image: “swift-mini”),

                                 MenuItem(name: “Lux D”, image: “lux-d”)

                                ]

 

        // Sub-menu gadgets for different tools

        let otherMenuItems = [ MenuItem(name: “Espresso AV”, image: “espresso-av”),

                                 MenuItem(name: “Espresso EP”, image: “espresso-ep”),

                                 MenuItem(name: “Pour Over”, image: “pourover”),

                                 MenuItem(name: “Steam”, image: “steam”)

                                ]

 

        return topMenuItems

    }()

 

    func subMenuItems(for id: MenuItem.ID) –> [MenuItem]? {

        guard let menuItem = mainMenuItems.first(the place: { $0.id == id }) else {

            return nil

        }

 

        return menuItem.subMenuItems

    }

 

    func menuItem(for categoryID: MenuItem.ID, itemID: MenuItem.ID) –> MenuItem? {

 

        guard let subMenuItems = subMenuItems(for: categoryID) else {

            return nil

        }

 

        guard let menuItem = subMenuItems.first(the place: { $0.id == itemID }) else {

            return nil

        }

 

        return menuItem

    }

}

The mainMenuItems array holds the pattern menu gadgets. Each subMenuItems and menuItem are helper strategies for trying up a particular class or menu merchandise.

Now that we’ve ready the info mannequin, let’s transfer onto the implementation of the navigation cut up view. Create a brand new file named TwoColumnSplitView.swift utilizing the SwiftUI view template. Replace the TwoColumnSplitView struct like this:

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

struct TwoColumnSplitView: View {

 

    @State non-public var selectedCategoryId: MenuItem.ID?

 

    non-public var dataModel = CoffeeEquipmenModel()

 

    var physique: some View {

        NavigationSplitView {

            Listing(dataModel.mainMenuItems, choice: $selectedCategoryId) { merchandise in

                HStack {

                    Picture(merchandise.picture)

                        .resizable()

                        .scaledToFit()

                        .body(width: 50, peak: 50)

                    Textual content(merchandise.title)

                        .font(.system(.title3, design: .rounded))

                        .daring()

                }

            }

 

            .navigationTitle(“Espresso”)

 

        } element: {

            if let selectedCategoryId,

               let categoryItems = dataModel.subMenuItems(for: selectedCategoryId) {

 

                Listing(categoryItems) { merchandise in

                    HStack {

                        Picture(merchandise.picture)

                            .resizable()

                            .scaledToFit()

                            .body(width: 50, peak: 50)

                        Textual content(merchandise.title)

                            .font(.system(.title3, design: .rounded))

                            .daring()

                    }

                }

                .listStyle(.plain)

                .navigationBarTitleDisplayMode(.inline)

 

            } else {

                Textual content(“Please choose a class”)

            }

        }

 

    }

}

The primary closure of NavigationSplitView presents the primary menu merchandise. We use a Listing view to loop via all mainMenuItems within the information mannequin and show every of the menu gadgets utilizing a HStack view.

We even have a state variable named selectedCategoryId, which is used to carry the chosen predominant menu merchandise.

For the element closure, that is the place the submenu merchandise is rendered. If a class is chosen, we name the subMenuItems methodology to get the submenu gadgets for that individual class. We then show the submenu gadgets utilizing Listing view. Conversely, if no class is chosen, we show a textual content message instructing the person to decide on a class.

When you made the adjustments, you need to see a two-column navigation UI within the Xcode preview.

swiftui-split-view-three-columns

Making a Three-Column Navigation Interface

Now that we’ve created a two-column navigation interface, let’s additional improve it to supply customers with a three-column navigation expertise. The additional column is used for displaying the picture of the chosen tools.

swiftui-navigation-split-view-three-column-demo

To transform the two-column navigation interface to three-column, we have to implement an extra parameter (i.e. content material) for the NavigationSplitView. Let’s create a brand new view named ThreeColumnSplitView like this:

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

49

50

51

52

53

54

55

56

57

58

struct ThreeColumnSplitView: View {

    @State non-public var selectedCategoryId: MenuItem.ID?

    @State non-public var selectedItem: MenuItem?

 

    non-public var dataModel = CoffeeEquipmenModel()

 

    var physique: some View {

        NavigationSplitView {

 

            Listing(dataModel.mainMenuItems, choice: $selectedCategoryId) { merchandise in

                HStack {

                    Picture(merchandise.picture)

                        .resizable()

                        .scaledToFit()

                        .body(width: 50, peak: 50)

                    Textual content(merchandise.title)

                        .font(.system(.title3, design: .rounded))

                        .daring()

                }

            }

 

            .navigationTitle(“Espresso”)

        } content material: {

 

            if let selectedCategoryId,

               let subMenuItems = dataModel.subMenuItems(for: selectedCategoryId) {

                Listing(subMenuItems, choice: $selectedItem) { merchandise in

                    NavigationLink(worth: merchandise) {

                        HStack {

                            Picture(merchandise.picture)

                                .resizable()

                                .scaledToFit()

                                .body(width: 50, peak: 50)

                            Textual content(merchandise.title)

                                .font(.system(.title3, design: .rounded))

                                .daring()

                        }

                    }

                }

                .listStyle(.plain)

                .navigationBarTitleDisplayMode(.inline)

 

            } else {

                Textual content(“Please choose a menu merchandise”)

            }

 

        } element: {

            if let selectedItem {

                Picture(selectedItem.picture)

                    .resizable()

                    .scaledToFit()

            } else {

                Textual content(“Please choose an merchandise”)

            }

        }

 

    }

}

Principally, the code within the content material closure ought to be similar to you. The content material parameter is designed for displaying the submenu gadgets. Thus, we use the Listing view to indicate the submenu gadgets for the chosen class.

When an merchandise is chosen within the submenu, the app exhibits the tools picture. That is achieved by the code written within the element closure.

After the code adjustments, the preview pane ought to present you a two-column format.

swiftui-navigation-empty

By default, the primary column is hidden. It’s essential faucet the menu button on the top-left nook to disclose it.

To manage the visibility of the cut up view, you possibly can declare a state variable of the sort NavigationSplitViewVisibility and set its worth to .all:

@State non-public var columnVisibility = NavigationSplitViewVisibility.all

When instantiating the NavigationSplitView, it has an choice parameter named columnVisibility. You may merely go the binding of columnVisibility to regulate the visibility of the columns.

swiftui-column-visiblity-split-view

The NavigationSplitViewVisibility.all worth tells iPadOS to show all of the three columns. There are different choices together with:

  • .computerized – Use the default main column visibility for the present machine. That is the default setting.
  • .doubleColumn – Present the content material column and element space of a three-column navigation cut up view.
  • .detailOnly – Cover the main two columns of a three-column cut up view. In different phrases, solely the element space exhibits.

Customizing the Model of Navigation Cut up Views

Have you ever examined the app in iPad Portrait? By default, the element space takes up the entire display screen when the iPad machine is in portrait mode. So, once you convey up the primary menu and submenu areas, the element space is hidden behind these two main columns.

swiftui-portrait-multiple-column

In case you don’t like this type, you possibly can change it by attaching the .navigationSplitViewStyle modifier to NavigationSplitView:

NavigationSplitView(columnVisibility: $columnVisibility) {

  .

  .

  .

}

.navigationSplitViewStyle(.balanced)

The default worth is ready to .computerized. In case you set the worth to .balanced, it reduces the element space such that the 2 main columns can seem on the similar time.

swiftui-splitview-multi-column-balanced

What’s Subsequent

This tutorial offers you an introduction to NavigationSplitView in iOS 16. It’s very straightforward to create multi-column navigation expertise for iPad customers. Even in the event you develop apps for iPhone customers, NavigationSplitView can adapt itself to suit the navigation expertise on narrower screens. For instance, when iPhone 13 Professional Max is in portrait mode, the cut up view exhibits a one-column navigation. In case you rotate the machine sideway, the cut up view adjustments to a multi-column format.

Subsequently, take a while to check this cut up view part and apply it to your app every time this type of UI is sensible.

For reference, if you wish to be taught extra about NavigationSplitView, you possibly can try this WWDC video.

In case you take pleasure in this text and need to dive deeper into SwiftUI, you might try our Mastering SwiftUI book.





Source link

Share30Tweet19
learningcode_x1mckf

learningcode_x1mckf

Recommended For You

The abstract Vapor service factory design pattern

by learningcode_x1mckf
February 1, 2023
0
The abstract Vapor service factory design pattern

I've written a number of articles about manufacturing unit design patterns on my weblog and this time I might like to speak a couple of particular one, which...

Read more

SwiftNIO tutorial – The echo server

by learningcode_x1mckf
January 27, 2023
0
SwiftNIO tutorial – The echo server

Intoducing SwiftNIO In the event you used a excessive degree net framework, corresponding to Vapor, up to now, you would possibly had some interplay with occasion loops...

Read more

Introducing – Vapor cheatsheet – The.Swift.Dev.

by learningcode_x1mckf
January 23, 2023
0
Introducing – Vapor cheatsheet – The.Swift.Dev.

Out there on Gumroad Thanks for supporting my work by buying the cheatsheet. 🙏 Download now A whole Vapor framework reference for novices. greater than...

Read more

iCloud Programming Tutorial for iOS: An Introduction

by learningcode_x1mckf
January 18, 2023
0
iCloud Programming Tutorial for iOS: An Introduction

Editor’s observe: This week, we work with Ziad Tamim once more to provide you an introduction of iCloud programming. You’ll learn to save and retrieve knowledge from iCloud.On...

Read more

Easy multipart file upload for Swift

by learningcode_x1mckf
January 18, 2023
0
Easy multipart file upload for Swift

I imagine that you've got already heard in regards to the well-known multipart-data add method that everybody likes to add recordsdata and submit type knowledge, but when not,...

Read more
Next Post
Wrap up and recommended talks – Hacking with Swift

Wrap up and recommended talks – Hacking with Swift

Leave a Reply Cancel reply

Your email address will not be published. Required fields are marked *

Related News

Improve Your Code’s Maintainability – Real Python

Improve Your Code’s Maintainability – Real Python

September 7, 2022
Build a Wordle Clone With Python and Rich – Real Python

Build a Wordle Clone With Python and Rich – Real Python

February 6, 2023
Saudi Arabia expresses solidarity with Indonesia after West Java earthquake

Saudi Arabia expresses solidarity with Indonesia after West Java earthquake

November 21, 2022

Browse by Category

  • C#
  • C++
  • Java
  • JavaScript
  • Python
  • Swift

RECENT POSTS

  • JobRunr, the Java Scheduler Library, Released Version 6.0 – InfoQ.com
  • An Introduction to Lodash and Its Benefits for JavaScript Developers – MUO – MakeUseOf
  • "Used properly, Python is not slower than C++" – eFinancialCareers (US)

CATEGORIES

  • C#
  • C++
  • Java
  • JavaScript
  • Python
  • Swift

© 2022 Copyright Learning Code

No Result
View All Result
  • Home
  • JavaScript
  • Java
  • Python
  • Swift
  • C++
  • C#

© 2022 Copyright Learning Code

Are you sure want to unlock this post?
Unlock left : 0
Are you sure want to cancel subscription?