簡體   English   中英

SwiftUI,如何在不重新創建視圖的情況下切換到視圖?

[英]SwiftUI, how to switch to a view without recreating it?

我的應用程序中有幾個不同的視圖,用戶可以在它們之間切換。 其中一個視圖是我創建的 SearchView。 此視圖可用於在文檔中搜索用戶指定的字符串,然后將 select 跳轉到其中一個搜索結果。 這是通過在用戶按下搜索按鈕時生成一堆搜索結果來實現的。 每個搜索結果都是其他視圖的組合,這會導致搜索過程和搜索結果生成過程需要相當長的時間,這在最初發生時很好。 我的問題是,如果用戶在搜索視圖中進行搜索,切換到另一個視圖,然后返回到搜索視圖,則重新創建所有搜索結果視圖需要很長時間。

如何將搜索視圖或搜索結果視圖保存在一些未清除的變量中以允許重復使用先前生成的搜索視圖結果?

我已經使用了一個環境 object 來存儲用於創建搜索結果的數據,例如搜索字符串、示例文本、章節等。這樣在切換回搜索視圖時不會重新創建數據,唯一的問題是查看自己。

這是搜索視圖結構:

@EnvironmentObject var modelView: ModelView

var OnJumpToSearchResult: ((Int) -> Void)?

var body: some View {
    ScrollView {
        HStack {
            //Search Field
            HStack {
                TextField("Search string here", text: $modelView.searchString)
            }
            .padding()
            .background(Color(.systemGray5))
            .cornerRadius(6)
            .padding(.horizontal)
            
            //Search Button
            Button(action: { modelView.searchResults = PerformSearch(pages: modelView.searchPages, pageHeadings: modelView.pageHeadings, searchString: modelView.searchString, sampleRadius: sampleRadius) }, label: {
                Text("Search")
                    .padding(.trailing)
            })
        }
        
        //Display Search Results
        if modelView.searchResults.isEmpty {
            EmptyView()
        }
        else
        {
            ForEach(modelView.searchResults, id: \.self) { searchResult in
                Button(action: {
                    if OnJumpToSearchResult != nil {
                        OnJumpToSearchResult?(searchResult.pageNumber - 1) }
                    
                }) {
                    VStack {
                        Text("\(searchResult.heading)")
                            .bold()
                        HStack {
                            HighlightedTextView(String(searchResult.sampleText), matching: modelView.searchString, caseInsensitive: true)
                            Spacer()
                            Text("s.\(searchResult.pageNumber)")
                        }
                        .padding()
                    }
                    
                    
                    Divider()
                        .background(Color(.systemGray4))
                        .padding(.leading)
                }
            }
        }
    }
}

搜索視圖的父視圖在初始化時初始化一個搜索視圖,並在它更新時重用它(而不是重新初始化一個新的)。

如果您的搜索視圖不依賴於其父視圖的任何內容,那么您只需在父視圖中創建一次,並且在父視圖中繼其子視圖時不會重新創建它(但如果父視圖是重新創建)

struct ViewThatRendersSearchView: View {
  let searchView = SearchView() // create it one time
  @State private var shouldShowSearchView = false
  var body: some View {
    if shouldShowSearchView {
      searchView // Won't be recreated each time
    } else {
      EmptyView()
    }
  }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM