[Video Summary] Ch. 8.13 - Location Search with Debouncing in SwiftUI (2024)
Mô tả nhanh
Video này hướng dẫn cách tạo một view tìm kiếm địa điểm có khả năng tái sử dụng trong SwiftUI, cho phép người dùng nhập địa điểm và thu hẹp kết quả tìm kiếm theo thời gian thực. Video cũng giới thiệu kỹ thuật "debouncing" để tránh gửi quá nhiều truy vấn tới Apple cùng một lúc.
Video
Mô tả chi tiết
Video này hướng dẫn cách tạo một view tìm kiếm địa điểm có khả năng tái sử dụng trong SwiftUI, cho phép người dùng nhập địa điểm và thu hẹp kết quả tìm kiếm theo thời gian thực. Video cũng giới thiệu kỹ thuật "debouncing" để tránh gửi quá nhiều truy vấn tới Apple cùng một lúc.
Dưới đây là các bước chính được thực hiện trong video:
-
Tạo PlaceLookupView:
- Tạo một file SwiftUI View mới tên
PlaceLookupView
. - Thêm một biến
@State private var searchText
để lưu trữ text tìm kiếm. - Sử dụng
NavigationStack
vàList
để hiển thị kết quả tìm kiếm (tạm thời hiển thị text input). - Thêm
.searchable
modifier để tạo search bar. - Thêm
.onChange
modifier để theo dõi thay đổi trongsearchText
và thực hiện tìm kiếm (chức năng tìm kiếm sẽ được thêm sau). - Thiết lập
listStyle
là.plain
. - Thêm
navigationTitle
vànavigationBarTitleDisplayMode
cho view. - Thêm một nút "Cancel" trong toolbar để dismiss view.
- Tạo một file SwiftUI View mới tên
-
Cập nhật ContentView:
- Tạo biến
@State private var sheetIsPresented
để kiểm soát việc hiển thị sheet. - Thêm
.sheet
modifier vào cuối VStack để presentPlaceLookupView
. - Thêm một nút để toggle
sheetIsPresented
và trình bàyPlaceLookupView
. - Chỉnh sửa nút "Cancel" trong
PlaceLookupView
thành "Dismiss".
- Tạo biến
-
Tạo Model Place:
- Tạo một file Swift mới tên
Place
, là model để chứa thông tin về địa điểm. - Import
MapKit
vàContacts
. - Tạo struct
Place
tuân theoIdentifiable
. - Tạo private property
mapItem
(MKMapItem) để lưu trữ thông tin địa điểm. - Khởi tạo Place với một
mapItem
. - Tạo computed properties:
name
(String): tên địa điểm.latitude
(CLLocationDegrees): vĩ độ.longitude
(CLLocationDegrees): kinh độ.address
(String): địa chỉ, lấy từCNPostalAddress
và chuyển đổi thành một chuỗi duy nhất.
- Tạo một file Swift mới tên
-
Tạo ViewModel PlaceLookupViewModel:
- Tạo file Swift mới tên
PlaceLookupViewModel
. - Import
MapKit
. - Thêm
@MainActor
và@Observable
để đảm bảo cập nhật UI trên main thread. - Tạo class
PlaceLookupViewModel
. - Thêm property
places
(Array) để lưu trữ kết quả tìm kiếm.
- Tạo file Swift mới tên
- Tạo hàm
search(text: String, region: MKCoordinateRegion)
(async, throws):- Tạo
MKLocalSearch.Request
vớinaturalLanguageQuery
vàregion
. - Tạo
MKLocalSearch
từ request. - Gọi hàm
search.start()
(await) để thực hiện tìm kiếm. - Kiểm tra xem có kết quả trả về không, nếu không sẽ throw lỗi.
- Map các
MKMapItem
trong response thành mảngPlace
.
- Tạo
- Kết nối PlaceLookupView với ViewModel:
- Thêm
@State var placeVM
(PlaceLookupViewModel) vàoPlaceLookupView
. - Thay đổi
List
để iterate quaplaceVM.places
. - Hiển thị
name
vàaddress
của mỗi place trong list. - Thêm
@State private var searchTask
(Task<Void,Never>?) để quản lý các task tìm kiếm. - Thêm
.onChange(of: searchText)
modifier để theo dõi thay đổi search text và thực hiện debouncing:- Cancel task đang thực thi (nếu có).
- Nếu search text rỗng, xoá mảng places hiện tại.
- Tạo task mới:
- Chờ 300ms (tránh gửi quá nhiều request).
- Kiểm tra task có bị cancel không, nếu có thì return.
- Gọi
placeVM.search()
với search text mới và tìm kiếm trong vùng hiện tại.
- Thêm
.onAppear
modifier để khởi tạosearchRegion
với vị trí hiện tại của thiết bị. - Thêm
.onDisappear
modifier để cancel các task đang thực thi khi view biến mất.
- Thêm
- Chỉnh sửa lại khởi tạo
PlaceLookupView
trongContentView
để truyền vào biếnlocationManager
.
-
Thêm hàm get Region vào LocationManager
- Thêm hàm
getRegionAroundCurrentLocation(radiusInMeters: CLlocationDistance = 10000) -> MKCoordinateRegion?
vàoLocationManager
để trả về 1 region xung quanh vị trí hiện tại với bán kính cho trước.
- Thêm hàm
-
Thử nghiệm trên Simulator
- Chạy ứng dụng trên simulator và test tính năng tìm kiếm địa điểm với các địa điểm khác nhau. Chú ý đến việc search radius sẽ ảnh hưởng đến kết quả tìm kiếm trên preview và trên simulator.
Video này cung cấp một hướng dẫn chi tiết về việc tạo một chức năng tìm kiếm địa điểm mạnh mẽ, kết hợp việc sử dụng các API của Apple, kỹ thuật debouncing và tốt nhất là khả năng tái sử dụng view tìm kiếm.
Chúc bạn có những trải nghiệm lập trình thú vị!