[SUI] 검색 바
Source: Dev.to
NavigationStack에서 검색 바
NavigationStack은 searchable 수식어를 사용하여 검색 바를 포함할 수 있습니다.
그 시그니처는 다음과 같습니다:
searchable(
text: Binding,
tokens: Binding? = nil,
suggestedTokens: [Token]? = nil,
placement: SearchFieldPlacement = .automatic,
prompt: String? = nil,
token: () -> TokenView? = { nil }
)
- text: 사용자가 입력한 텍스트.
- tokens: 표시된 토큰을 추적합니다.
- suggestedTokens: 제안된 토큰 목록.
- placement: 바의 위치 (
automatic,navigationBarDrawer,sidebar,toolbar등). - prompt: 플레이스홀더.
- token: 토큰을 표시하기 위한 뷰.
기본 사용법
struct Person: Identifiable {
let id = UUID()
let name: String
}
private let people: [Person] = [
.init(name: "David Goyes"),
.init(name: "Midoriya Izuku"),
.init(name: "Tanjiro Kamado"),
.init(name: "David Beckham"),
]
struct ContentView: View {
@State private var searchText: String = ""
private var filteredPeople: [Person] {
if searchText.isEmpty {
people
} else {
people.filter { $0.name.localizedStandardContains(searchText) }
}
}
var body: some View {
NavigationStack {
List(filteredPeople) { person in
Text(person.name)
}
.navigationTitle("Personas")
.searchable(text: $searchText, prompt: "¿A quién busca?")
}
}
}
iOS 26에서는 기본적으로 바가 하단에 배치됩니다(
toolbar와 동일). first responder가 되면 키보드 위에 나타납니다.
onChange로 목록 업데이트
필터링된 결과를 저장하고 싶다면, 수동으로 업데이트해야 합니다:
struct ContentView: View {
@State private var searchText: String = ""
@State private var filteredPeople: [Person] = []
var body: some View {
NavigationStack {
List(filteredPeople) { person in
Text(person.name)
}
.navigationTitle("Personas")
.searchable(text: $searchText, prompt: "¿A quién busca?")
.onChange(of: searchText, initial: true) {
filterPeople()
}
}
}
private func filterPeople() {
filteredPeople = searchText.isEmpty
? people
: people.filter { $0.name.localizedStandardContains(searchText) }
}
}
검색창 위치
automatic/toolbar: 하단 바에 항상 표시됩니다.navigationBarDrawer: 리스트를 위로 스크롤하면 사라지고 아래로 스크롤하면 다시 나타납니다.
네비게이션 바에 항상 표시하려면:
struct ContentView: View {
@State private var searchText: String = ""
private var filteredPeople: [Person] {
if searchText.isEmpty {
people
} else {
people.filter { $0.name.localizedStandardContains(searchText) }
}
}
var body: some View {
NavigationStack {
List(filteredPeople) { person in
Text(person.name)
}
.navigationTitle("Personas")
.searchable(
text: $searchText,
placement: .navigationBarDrawer(displayMode: .always),
prompt: "¿A quién busca?"
)
}
}
}
searchFocused를 사용한 프로그래밍 방식 포커스 제어
searchFocused(_:)와 @FocusState를 이용해 검색 바의 포커스를 제어할 수 있습니다:
struct ContentView: View {
@State private var searchText: String = ""
@FocusState private var isFocused: Bool // <-- 바의 포커스
private var filteredPeople: [Person] {
if searchText.isEmpty {
people
} else {
people.filter { $0.name.localizedStandardContains(searchText) }
}
}
var body: some View {
NavigationStack {
List(filteredPeople) { person in
Text(person.name)
}
.navigationTitle("Personas")
.toolbar {
ToolbarItem(placement: .topBarTrailing) {
Button("Buscar", systemImage: "magnifyingglass") {
isFocused = true // 바에 포커스를 맞춤
}
}
}
.searchable(
text: $searchText,
placement: .navigationBarDrawer(displayMode: .automatic),
prompt: "¿A quién busca?"
)
.searchFocused($isFocused) // 포커스 제어
}
}
}
toolbar에 있는 “Buscar” 버튼을 누르면 isFocused가 true로 설정되어 키보드가 나타나고 커서가 검색 바에 위치합니다.