swiftswiftuixcode12swiftui-environmentswiftui-state

How to switch between views using @State and fullScreenCover in SwiftUI


I'm trying to figure out how to switch between views using @State and fullScreenCover in SwiftUI

I have a main view and 2 simple views (View1 and View2). View1 must open on the tap of the "Show view 1" button, and View2 when typing on the "Show view 2" button. I also created 2 @State variables for this to work and initialized it with a .View1 (ActiveFullscreenview enum):

 @State private var showFullscreenView = false
 @State private var activeFullscreenView: ActiveFullscreenView = .View1

The problem is that it constantly showing the View1 even when I tap on the Show view 2 Button. I thought that when tapping on the button and giving the activeFullscreenView variable a value of .View2 , it should change the variable and show the fullScreenView.

I supposed that it was because I called the showFullscreenView and it changed the variable and after that the default value was .View1 so it didn't change it.

tried this too:

 self.showFullscreenView = true
 self.activeFullscreenView = .View2
          

The second assumption was that I shouldn't give this variable the initial value. But in this case it adds some additional initialisation code that is not convenient:

 @State private var activeFullscreenView: ActiveFullscreenView = .View1 

Currently I have the following code that has the described issue:

import SwiftUI

struct MainView: View {
    
    enum ActiveFullscreenView {
        case View1, View2
    }
    
    @State private var showFullscreenView = false
    @State private var activeFullscreenView: ActiveFullscreenView = .View1
    
    var body: some View {
        
        ZStack {
            
            VStack {
            
            // Button to show View 1 in FullScreen
            Button("Show view 1", action: {
                
                self.activeFullscreenView = .View1
                self.showFullscreenView = true
               
            })
            
            // Button to show View 2 in FullScreen
            Button("Show view 2", action: {
                
                self.activeFullscreenView = .View2
                self.showFullscreenView = true
               
            })
                
            }
            
        }
        .fullScreenCover(isPresented: $showFullscreenView) {
            
            switch self.activeFullscreenView {
            case .View1:
                
                Text("View1")
       
            case .View2:
                
                Text("View2")
             
            }
            
        }
        
    }
}

struct MainView_Previews: PreviewProvider {
    static var previews: some View {
        MainView()
    }
}

Any help related to solving the problem appreciated. Convenient ways ways about how to achieve the same results of showing separate views using fullscreenCover appreciated.

Working in Xcode 12.4, latest iOS 14


Solution

  • With the help of @jnpdx who provided This Answer that is Similar to My problem the problem is solved. Here is the code. As long as fullScreenCover and sheet are both modals, I renamed enum to ModalView:

    struct MainView: View {
        
        // enum to decide which view to present:
        enum ModalView: String, Identifiable { // Identifiable
            
            case View1, View2
            
            var id: String {
                return self.rawValue
            }
        }
        
        @State var activeModalView : ModalView? = nil
        
        var body: some View {
            
            ZStack {
                
                VStack {
                    
                    // Button to show View 1
                    Button("Show view 1", action: {
                        
                        self.activeModalView = .View1
                        
                    })
                    
                    // Button to show View 2
                    Button("Show view 2", action: {
                        
                        self.activeModalView = .View2
                        
                    })
                    
                }
                
            } // use fullScreenCover or sheet depending on your needs
            .fullScreenCover(item: $activeModalView) { activeModalValue in
                
                switch activeModalValue {
                case .View1:
                    
                    Text("View1")
    
                case .View2:
                    
                    Text("View2")
                    
                }
            }
            
        }
        
    }