- Published on
SwiftUI crypto app — HomeView-da ro'yxatlar va ViewModel-ni sozlash
- Authors
- Name
- ShoxruxC
- @iOSdasturchi
SwiftUI crypto app — HomeView-da ro'yxatlar va ViewModel-ni sozlash
Ushbu darsda biz ilovamizning MVVM arxitekturasini yaratishni boshlaymiz: ma'lumotlar bilan ishlovchi HomeViewModelni yozamiz va uni butun ilova bo'ylab tarqatish uchun EnvironmentObject mexanizmidan foydalanamiz.
Shuningdek, HomeViewda foydalanuvchining shaxsiy portfeli va umumiy bozor narxlari ro'yxatlarini chiroyli gorizontal animatsiya (transition) yordamida almashtirishni sozlaymiz.
1. HomeViewModel yaratish
home/viewmodels papkasi ichida HomeViewModel.swift nomli yangi fayl ochamiz. Bu klass ilova ma'lumotlarini boshqarishi uchun ObservableObject protokoliga moslanadi:
import Foundation
import Combine
class HomeViewModel: ObservableObject {
// Ilovadagi barcha tangalar va foydalanuvchi portfelidagi tangalar ro'yxati
@Published var allCoins: [CoinModel] = []
@Published var portfolioCoins: [CoinModel] = []
init() {
// Tarmoqdan yuklashni simulyatsiya qilish uchun 2 soniyali kechikishdan foydalanamiz
addSubscribers()
}
private func addSubscribers() {
// Hozircha tarmoq ulanmaganligi uchun, 2 soniyadan keyin mock ma'lumotlarni ro'yxatlarga qo'shamiz
DispatchQueue.main.asyncAfter(deadline: .now() + 2.0) {
self.allCoins.append(DeveloperPreview.instance.coin)
self.portfolioCoins.append(DeveloperPreview.instance.coin)
}
}
}
2. ViewModel-ni ilovaga va preview-ga integratsiya qilish
Biz bir nechta turli ekranlarda ayni bitta ma'lumotlar manbasidan foydalanamiz. Shuning uchun ViewModel obyektini bir marta yaratib, butun loyiha bo'ylab tarqatish uchun Environment Objectdan foydalanamiz.
App.swift faylida sozlash
@main
struct SwiftfulCryptoApp: App {
// Asosiy ViewModel obyektini yaratamiz
@StateObject private var vm = HomeViewModel()
var body: some Scene {
WindowGroup {
NavigationView {
HomeView()
.navigationBarHidden(true)
}
// Butun navigatsiya iyerarxiyasiga ViewModelni ulash
.environmentObject(vm)
}
}
}
PreviewProvider uchun ulanish (PreviewProvider.swift)
DeveloperPreview klassiga ViewModel mock obyektini qo'shib qo'yamiz:
class DeveloperPreview {
static let instance = DeveloperPreview()
private init() {}
let coin = CoinModel(...)
// Mock ViewModel
let homeVM = HomeViewModel()
}
3. HomeView-da ro'yxatlarni va animatsiyalarni shakllantirish
Endi HomeView.swift faylida ViewModel-ni @EnvironmentObject orqali chaqiramiz va allCoinsList hamda portfolioCoinsList ro'yxatlarini dizayn qilamiz.
Ro'yxatlar almashayotganda chapga va o'ngga surilishi uchun .transition(.move(edge: .leading)) va .transition(.move(edge: .trailing)) modifikatorlaridan foydalanamiz.
import SwiftUI
struct HomeView: View {
// Atrof-muhitdan (Environment) ViewModelni qabul qilamiz
@EnvironmentObject private var vm: HomeViewModel
@State private var showPortfolio: Bool = false
var body: some View {
ZStack {
Color.theme.background
.ignoresSafeArea()
VStack {
homeHeader
columnTitles
if !showPortfolio {
// Umumiy narxlar ro'yxati (chapga suriladi)
allCoinsList
.transition(.move(edge: .leading))
}
if showPortfolio {
// Portfel ro'yxati (o'ngga suriladi)
portfolioCoinsList
.transition(.move(edge: .trailing))
}
Spacer(minLength: 0)
}
}
}
}
4. Ro'yxat ustunlari nomlari (Column Titles) va ro'yxat qismlari
HomeView faylining ostida extension yaratib, ro'yxat elementlari va ustun nomlarini ajratib yozamiz. Bu body kodini o'qishni juda osonlashtiradi:
extension HomeView {
// Ustun nomlari
private var columnTitles: some View {
HStack {
Text("Coin")
Spacer()
if showPortfolio {
Text("Holdings")
}
Text("Price")
.frame(width: UIScreen.main.bounds.width / 3.5, alignment: .trailing)
}
.font(.caption)
.foregroundColor(Color.theme.secondaryText)
.padding(.horizontal)
}
// Barcha tangalar ro'yxati
private var allCoinsList: some View {
List {
ForEach(vm.allCoins) { coin in
CoinRowView(coin: coin, showHoldingsColumn: false)
.listRowInsets(.init(top: 10, leading: 0, bottom: 10, trailing: 10))
}
}
.listStyle(.plain)
}
// Portfeldagi tangalar ro'yxati
private var portfolioCoinsList: some View {
List {
ForEach(vm.portfolioCoins) { coin in
CoinRowView(coin: coin, showHoldingsColumn: true)
.listRowInsets(.init(top: 10, leading: 0, bottom: 10, trailing: 10))
}
}
.listStyle(.plain)
}
}
Ushbu bosqichdan so'ng ilovani ishga tushirganimizda, 2 soniya davomida bo'sh ekran ko'rinadi va ma'lumotlar "yuklangach" ro'yxatda Bitcoin ko'rinadi. O'ngga surilganda esa portfeldagi Bitcoin va uning umumiy summasi ko'rsatiladi.
Keyingi darsda biz nihoyat internetdan (API) jonli ma'lumotlarni yuklab olishni boshlaymiz! 🚀