إنشاء كائن Objective -C يلف كائنًا آخر بنفس الواجهة - مشكلات KVC/KVO
-
01-10-2019 - |
سؤال
أحتاج إلى إنشاء كائن في التسلسل الهرمي لفئة واحدة يلف كائنًا من كائن مختلف. كلاهما لديهما واجهات متشابهة للغاية ، وأود أن يكون لديّ رسائلي إلى الأمام تلقائيًا ، ولا يتعرف على هدفها بدلاً من تنفيذ خصائصها الخاصة. حصلت على هذا للعمل باستخدام شيء مثل هذا:
- (id)forwardingTargetForSelector:(SEL)sel { if ([self.wrappedObject respondsToSelector:sel]) return self.wrappedObject; return self; }
ولكن هذا لا يعمل مع ترميز القيمة الرئيسية. كيف يمكنني أن أقوم بتطبيق Wrapper لتنفيذ ترميز قيمة المفاتيح بطريقة تستخدم خصائص كائنها ملفوف؟
المحلول
يجب عليك الكتابة فوقها valueForKey:
و setValue:forKey:
. مثال:
- (id)valueForKey:(NSString *)key {
if (/* wrapped object has key */)
return [self.wrappedObject valueForKey: key];
else
return [super valueForKey: key];
}
سيكون الجزء الصعب هو تحديد المفاتيح التي ينفذها الكائن ملفوف. الطريقة السهلة هي أن ترمز لهم ، لكن هذا ليس لطيفًا جدًا. إذا كنت ترغب في القيام بذلك عام ، فستفعل شيئًا باستخدام واجهات برمجة تطبيقات الانعكاس لـ Objective-C. هنا فكرتان:
جميع خصائصك معلنة بالفعل. يمكنك استخدام وظيفة وقت التشغيل class_getProperty للتحقق من وجودها واستخراج معلومات إضافية اختياريًا. يمكن أن يبدو الشيك هكذا:
if (class_getProperty([self.wrappedObject class], [key UTF8String]) != nil) {...}
.يمكن أن يكون للممتلكات الخاصة بك ملحقات فقط. ثم يجب عليك بناء المحددات من المفتاح والاستخدام
[self.wrappedObject respondsToSelector: ...]
تماما كما فعلت من قبل. اسم getter هو المفتاح بالإضافة إلى القولون. ومع ذلك ، فإن المشكلة في هذا هي الخصائص التي لها اسم Getter/Setter مختلف. الخيار الأول هو بالتأكيد الأفضل.