@ObservedObject — SwiftUI-də kənardan ötürülmüş ObservableObject nüsxəsini müşahidə etmək üçün Property Wrapper-dır. @StateObject-dən fərqli olaraq, @ObservedObject obyekt yaratmır — o, mövcud olanın dəyişikliklərinə abunə olur. Apple Developer Documentation (2025)-yə görə, @ObservedObject valideynə məxsus məlumatları izləməli olan övlad görüntülərində istifadə olunur. @ObservedObject obyektin həyat dövrünü idarə etmədən reaktiv əlaqə təmin edir.
Başlıca
@ObservedObject — görüntünü ObservableObject dəyişikliklərinə abunə edən Property Wrapper-dır. ObservableObject — Combine çərçivəsindən objectWillChange publishernin tətbiqini tələb edən protokol. @Published ilə işarələnmiş hər hansı xassə ObservableObject daxilində dəyişdikdə, publisher siqnal göndərir və SwiftUI @ObservedObject vasitəsilə abunə olunmuş bütün görüntüləri yenidən çəkir.
@ObservedObject-in əsas xüsusiyyəti sahiblik olmamasıdır. Görüntü obyektin yaradılması və ya məhv edilməsi üçün cavabdeh deyil. Obyekt valideyn görüntüsündə (@StateObject vasitəsilə) yaradılır və ya @EnvironmentObject vasitəsilə yeridilir. Övlad görüntüsü yalnız dəyişiklikləri müşahidə edir və yeniləmələri alır. Obyekt valideyndə əvəz edilərsə, @ObservedObject yeni nüsxəyə keçir.
@ObservedObject məlumat paylaşımı ssenariləri üçün uyğundur: istifadəçi modeli, ümumi parametrlər, serverə qoşulma vəziyyəti. İyerarxiyanın müxtəlif səviyyələrindəki bir neçə görüntü eyni məlumatları göstərməli olduqda, hər görüntüdəki @ObservedObject bir mənbəyə müstəqil, lakin uyğun abunələr yaradır.
@ObservedObject və @StateObject arasındakı fərq SwiftUI müsahibələrində ən çox verilən suallardan biridir. Əsas qayda: @StateObject obyekti yaradır və sahibdir, @ObservedObject isə mövcud olanı müşahidə edir. Bu qaydanın pozulması gözlənilməz məlumat itkisinə və ya qoşa iniziallaşmaya səbəb olur.
| Xüsusiyyət | @StateObject | @ObservedObject |
|---|---|---|
| Obyektin yaradılması | Bəli, görüntünün iniziallaşması zamanı | Xeyr, hazır alır |
| Sahiblik | Cari görüntü | Valideyn komponent |
| Tək nüsxə | Bəli, bütün həyat dövrü boyunca | Xeyr, əvəz edilə bilər |
| Renderdə yenidən yaradılma | Xeyr, qorunur | Valideyndən asılıdır |
| Harada istifadə olunur | Kök görüntü-sahib | Övlad görüntülər |
@StateObject obyektin bir dəfə yaradıldığına və görüntü strukturunun təkrar iniziallaşmalarından sağ çıxdığına zəmanət verir. @ObservedObject obyekti kənardan alır və valideyn strukturunun hər iniziallaşmasında yenidən yaradılır. Valideyn obyekt üçün @StateObject istifadə edərsə, övlad görüntülər təhlükəsiz şəkildə @ObservedObject tətbiq edə bilər — obyekt bütün iyerarxiyada vahid olacaq.
@ObservedObject-in izləmə mexanizmi Combine və ObservableObject protokoluna əsaslanır. İnitializasiya zamanı SwiftUI objectWillChange publisherni çağırır — obyekt @Published xassəsini dəyişməzdən əvvəl siqnal göndərməlidir. Combine siqnalı SwiftUI-nin asılılıq qrafikinə ötürür, o da bütün asılı görüntüləri yeniləmə tələb edən kimi qeyd edir. Bu, dəyər dəyişməzdən əvvəl sinxron şəkildə baş verir.
class WeatherService: ObservableObject {
@Published var temperature: Double = 22.0
@Published var city: String = "Moscow"
}
struct WeatherView: View {
@ObservedObject var weather: WeatherService
var body: some View {
VStack {
Text("\\(weather.city)")
Text("\\(weather.temperature)°C")
}
}
}
Listinqdə WeatherService iki @Published xassəsi olan ObservableObject-dir. WeatherView @ObservedObject var weather: WeatherService elan edir, nüsxəni valideyndən alır. Temperature dəyişdikdə, objectWillChange yeni dəyər qoyulmazdan əvvəl işə düşür, SwiftUI WeatherView-i yenidən çəkir və cari temperatur göstərilir. Abunə avtomatik olaraq SwiftUI tərəfindən idarə olunur — tərtibatçı sink və ya dispose çağırmağa ehtiyac duymur.
Birinci nümunə — modelin iniziallaşdırıcı vasitəsilə ötürülməsi. Valideyn ObservableObject-i @StateObject vasitəsilə yaradır və onu övlad görüntülərinə @ObservedObject kimi ötürür. Bu, kök görüntünün modelin həyat dövrünü idarə etdiyi və bütün daxil edilmiş komponentlərin dəyişikliklərə abunə olduğu standart iyerarxik məlumat ötürülməsidir.
İkinci nümunə — EnvironmentObject, SwiftUI Environment vasitəsilə @ObservedObject-in qlobal versiyası. Obyekt səhnə və ya kök görüntü səviyyəsində yeridilir və bütün övlad komponentlərə iniziallaşdırıcılar vasitəsilə açıq ötürülmədən avtomatik olaraq əlçatan olur. Övlad görüntü daxilində @EnvironmentObject @ObservedObject kimi işləyir, lakin obyekti mühitdən alır.
Üçüncü nümunə — bir neçə ObservableObject-in kompozisiyası. Mürəkkəb tətbiqlərdə görüntü bir neçə obyekti müşahidə edə bilər: @ObservedObject var user: UserService, @ObservedObject var network: NetworkMonitor. Bu, məsuliyyəti xidmətlər arasında bölüşdürür və hər bir komponentin test edilə bilməsini təmin edir.
struct DashboardView: View {
@ObservedObject var user: UserViewModel
@ObservedObject var network: NetworkMonitor
var body: some View {
VStack {
Text("Xoş gəldiniz, \\(user.name)")
HStack {
Circle()
.fill(network.isConnected ? Color.green : Color.red)
.frame(width: 10, height: 10)
}
}
}
}
DashboardView UserViewModel və NetworkMonitor-u müşahidə edir. Hər bir obyekt öz məlumat sahəsinə görə cavabdehdir və müstəqil olaraq görüntüyə dəyişikliklər barədə məlumat verir. Şəbəkə kəsilərsə, NetworkMonitor isConnected-i dəyişir və SwiftUI DashboardView-i yenidən çəkir, göstəricinin rəngini yeniləyir. ObservableObject kompozisiyası SwiftUI tətbiqlərində məlumatların təşkili üçün üstünlük verilən üsuldur.
@Published — Combine-dən ObservableObject daxilindəki xassəyə avtomatik olaraq naşir əlavə edən Property Wrapper-dır. @Published xassəsi dəyişikdə, Combine objectWillChange publisher vasitəsilə hadisə yaradır. SwiftUI @ObservedObject və ya @StateObject istifadə edərkən bu publishera abunə olur və hər yeni dəyərdə görüntüyü yenidən çəkir.
@Published bütün növləri, o cümlədən opsional, kolleksiyalar və fərdi strukturları dəstəkləyir. Lakin kolleksiyalar (massivlər, lüğətlər) üçün SwiftUI yalnız istinadın dəyişməsini izləyir, məzmunun dəyişməsini yox. Elementin əlavə edilməsini və ya silinməsini aşkar etmək üçün kolleksiyanı tamamilə yenidən təyin etməli və ya manual objectWillChange.send() ilə ObservableObject istifadə etməlisiniz.
Vacib detal: @Published yalnız ObservableObject-i tətbiq edən sinif daxilində yerləşməlidir. @Published-dən ObservableObject xaricində istifadə etmək tərtib xətasına səbəb olur. Həmçinin @Published tənbəl inicializasiya (lazy var) və ya hesablanmış xassələrə (computed property) tətbiq edilə bilməz.
Ən kritik səhv @ObservedObject-dən obyekt yaratmaq üçün istifadə etməkdir. Valideyn görüntüsündə @ObservedObject var model = UserViewModel() yazsanız, hər renderdə yeni UserViewModel nüsxəsi yaradılacaq. Məlumatlar itiriləcək və @Published abunələri yenidən yaradılacaq. Həmişə yaratmaq üçün @StateObject, hazır obyekti almaq üçün isə yalnız @ObservedObject istifadə edin.
İkinci səhv — @Published xassələrinin əsas axından kənarda dəyişdirilməsi. ObservableObject Combine-dən istifadə edir, o, dəyişikliklərin əsas axında (main actor) göndərilməsini tələb edir. @Published-i fon növbəsində dəyişdirsəniz, SwiftUI görüntünü uyğun olmayan anda yenidən çəkə bilər, race conditions yaradır. Yeniləmə üçün DispatchQueue.main.async və ya @MainActor istifadə edin.
Üçüncü problem — tsiklik yeniləmələr. @Published dəyişikliyi yenidən @Published-i dəyişən yan təsirlərə səbəb olarsa, sonsuz yenidən çəkmə dövrü yaranır. Həll yolu: qoruyucu bayraqlardan (isUpdating) istifadə etmək və ya məntiqi aydın məsuliyyət sərhədləri olan müxtəlif ObservableObject-lərə bölmək.
Tez-tez verilən suallar
Bəli, SwiftUI @ObservedObject var model: UserViewModel? dəstəkləyir. Lakin görüntü obyekt nil olduğu müddətdə dəyişikliklərə abunə olmayacaq. Dəyər təyin edildikdə, abunə avtomatik olaraq aktivləşir.
@ObservedObject obyekti iniziallaşdırıcı vasitəsilə alır, @EnvironmentObject isə SwiftUI Environment vasitəsilə. @EnvironmentObject konstruktorlar vasitəsilə açıq ötürülmə tələb etmir, lakin obyekt iyerarxiyanın yuxarı səviyyəsində yeridilməlidir.
Xassəni dəyişməzdən əvvəl objectWillChange.send()-i çağırın. Bu, @Published uyğun olmadıqda faydalıdır (məsələn, hesablanmış xassələr və ya mutasiyadan əvvəl dəyişiklik barədə məlumat vermək lazım olan kolleksiya əməliyyatları üçün).
@ObservedObject və @Published istinadın dəyişməsini izləyir, kolleksiya məzmununun mutasiyasını yox. Yenidən çəkmə üçün massivi yenidən təyin etməlisiniz: items.append(newItem) → items = items və ya mutasiyadan əvvəl objectWillChange.send() istifadə edin.
Xeyr, @ObservedObject yalnız View protokolunu tətbiq edən tiplər daxilində mövcud olan SwiftUI Property Wrapper-dır. Adi strukturlar üçün Combine-dən birbaşa ObservableObjectPublisher ilə istifadə edin.
Nəticə
Açar təslim mobil tətbiq hazırlayacağıq
IT Sectr 2017-ci ildən startaplar və bizneslər üçün iOS və Android tətbiqləri yaradır. Sizə məsləhət verəcəyik və ən yaxşı həlli təklif edəcəyik.
Həm də oxuyun