मैं n8gray के उत्तर पर जोड़ना चाहूंगा कि कुछ मामलों में आपको setNeedsLayout
बाद में कॉल करना होगा layoutIfNeeded
।
उदाहरण के लिए मान लें कि आपने UIView का विस्तार करने वाला एक कस्टम दृश्य लिखा है, जिसमें सबव्यू की स्थिति जटिल है और इसे ऑटोरेस्पिरिंगमास्क या iOS6 AutoLayout के साथ नहीं किया जा सकता है। कस्टम पोजिशन को ओवरराइड करके किया जा सकता है layoutSubviews
।
एक उदाहरण के रूप में, मान लें कि आपके पास एक कस्टम दृश्य है जिसमें एक contentView
संपत्ति है और एक edgeInsets
संपत्ति है जो सामग्री दृश्य के चारों ओर मार्जिन सेट करने की अनुमति देती है। layoutSubviews
इस तरह दिखेगा:
- (void) layoutSubviews {
self.contentView.frame = CGRectMake(
self.bounds.origin.x + self.edgeInsets.left,
self.bounds.origin.y + self.edgeInsets.top,
self.bounds.size.width - self.edgeInsets.left - self.edgeInsets.right,
self.bounds.size.height - self.edgeInsets.top - self.edgeInsets.bottom);
}
यदि आप चाहते हैं कि जब भी आप edgeInsets
संपत्ति बदलते हैं तो फ्रेम परिवर्तन को चेतन करने में सक्षम हों , आपको edgeInsets
निम्नानुसार सेटर को ओवरराइड करना होगा और setNeedsLayout
इसके बाद कॉल करना होगा layoutIfNeeded
:
- (void) setEdgeInsets:(UIEdgeInsets)edgeInsets {
_edgeInsets = edgeInsets;
[self setNeedsLayout]; //Indicates that the view needs to be laid out
//at next update or at next call of layoutIfNeeded,
//whichever comes first
[self layoutIfNeeded]; //Calls layoutSubviews if flag is set
}
इस तरह, यदि आप निम्नलिखित करते हैं, यदि आप एनीमेशन ब्लॉक के अंदर किनारे संपत्ति को बदलते हैं, तो सामग्री दृश्य का फ्रेम परिवर्तन एनिमेटेड होगा।
[UIView animateWithDuration:2 animations:^{
customView.edgeInsets = UIEdgeInsetsMake(45, 17, 18, 34);
}];
यदि आप setEdgeInsets पद्धति में लेआउट में कॉल को जोड़ नहीं पाते हैं, तो एनीमेशन काम नहीं करेगा क्योंकि लेआउटसुब्यू को अगले अपडेट चक्र पर कॉल किया जाएगा, जो एनीमेशन ब्लॉक के बाहर कॉल करने के लिए समान है।
यदि आप setEdgeInsets विधि में केवल लेआउटIfNeeded कहते हैं, तो कुछ भी नहीं होगा क्योंकि setNeedsLayout ध्वज सेट नहीं है।