2011-11-29 7 views
22

मैं एक UIView वस्तु घूमता कि CALayer का उपयोग कर के परिणत है:एंटीएलियासिंग CALayer के बदलने का उपयोग कर परिवर्तन के बाद UIView के किनारों

// Create uiview object. 
UIImageView *block = [[UIImageView alloc] initWithFrame....] 

// Apply rotation. 
CATransform3D basicTrans = CATransform3DIdentity; 
basicTrans.m34 = 1.0/-distance; 
blockImage.layer.transform = CATransform3DRotate(basicTrans, rangle, 1.0f, 0.0f, 0.0f); 

वस्तु के किनारों घुमाने के बाद एंटीलायज़िंग़ नहीं हैं। मुझे उन्हें antialias की जरूरत है। कृपया मेरी मदद करें। यह कैसे किया जा सकता है?

उत्तर

41

ऐसा करने का एक तरीका छवि को एक और दृश्य के अंदर रखकर 5 पिक्सेल बड़ा है। , तब

view.layer.borderWidth = 3; 
view.layer.borderColor = [UIColor clearColor].CGColor; 
view.layer.shouldRasterize = YES; 
view.layer.rasterizationScale = [[UIScreen mainScreen] scale]; 

इस जनक दृश्य के अंदर अपने UIImageView जगह है और यह केंद्र (प्रत्येक किनारे के आसपास 2.5 पिक्सल के साथ): बड़ा दृश्य एक पारदर्शी रास्टराज़ सीमा कि UIImageView के सिरों को सम होगा होना चाहिए।

अंत में, छवि दृश्य के बजाय मूल दृश्य घुमाएं।

यह बहुत अच्छी तरह से काम करता है - आप पूरी चीज को कक्षा में भी शामिल कर सकते हैं जो पदानुक्रम बनाता है।

+9

रेटिना स्क्रीन पर धुंध से बचने के लिए आप 'view.layer.rasterizationScale = [[UIScreen mainScreen] पैमाने] जोड़ना चाहेंगे। –

+0

यह टिप्पणी उत्तर का हिस्सा होना चाहिए। 'कंधा' संपत्ति सेट करना पर्याप्त नहीं है! –

+0

आप सही हैं। किया हुआ। – tarmes

30

बस इस कुंजी-मूल्य जोड़ी को अपने पर जोड़ें Info.plist: UIViewEdgeAntialiasingYES पर सेट करें।

+1

यह हत्यारा है! – orkenstein

+0

शानदार! प्रदर्शन का कोई विचार हिट? – horseshoe7

+0

यह प्रदर्शन जुर्माना के साथ आता है, अगर आप कर सकते हैं तो इससे बचें। –

3

जेड-अक्ष के चारों ओर घूमते समय मुझे एक समान समस्या थी। कंधे को व्यवस्थित करना = हाँ ने जंजीर किनारों को रोक दिया, हालांकि यह प्रदर्शन लागत पर आया। मेरे मामले में मैं विचारों (और इसकी परतों) का फिर से उपयोग कर रहा था और कंधे को बनाए रखना = हाँ चीजों को धीमा कर रहा था।

समाधान, रास्टराइजेशन को बंद करने के बाद, मुझे इसकी आवश्यकता नहीं होने के बाद सही था। हालांकि, एनीमेशन किसी अन्य धागे पर चलता है, इसलिए एनीमेशन पूरा होने पर जानने का कोई तरीका नहीं था ... जब तक मुझे एक बेहद उपयोगी कैट्रानैक्शन विधि के बारे में पता नहीं चला। यह एक वास्तविक कोड है जिसका मैंने उपयोग किया था और इसे इसके उपयोग को स्पष्ट करना चाहिए:

// Create a key frame animation 
CAKeyframeAnimation *wiggle = [CAKeyframeAnimation animationWithKeyPath:@"transform"]; 
NSInteger frequency = 5; // Higher value for faster vibration 
NSInteger amplitude = 25; // Higher value for lower amplitude 
// Create the values it will pass through  
NSMutableArray *valuesArray = [[NSMutableArray alloc] init]; 
NSInteger direction = 1; 

[valuesArray addObject:@0.0]; 

for (NSInteger i = frequency; i > 0; i--, direction *= -1) { 
    [valuesArray addObject:@((direction * M_PI_4 * (CGFloat)i/(CGFloat)amplitude))]; 
} 

[valuesArray addObject:@0.0]; 
[wiggle setValues:valuesArray]; 

// Set the duration 
[wiggle setAdditive:YES]; 
[wiggle setValueFunction:[CAValueFunction functionWithName:kCAValueFunctionRotateZ]]; 
[wiggle setDuration:0.6]; 

// Turn on rasterization to prevent jagged edges (anti-aliasing issues) 
viewToRotate.layer.shouldRasterize = YES; 

// ************ Important step ************** 
// Very usefull method. Block returns after ALL animations have completed. 
[CATransaction setCompletionBlock:^{ 
    viewToRotate.layer.shouldRasterize = NO; 
}]; 
// Animate the layer 
[viewToRotate.layer addAnimation:wiggle forKey:@"wiggleAnimation"]; 

मेरे लिए एक आकर्षण की तरह काम करता था।

मैंने निहित एनिमेशन के साथ इसका उपयोग करने की कोशिश नहीं की है (यानी एनीमेशन जो गैर-दृश्य संबंधित परत के लिए एनिमेटेबल प्रॉपर्टी में मूल्य परिवर्तन के कारण होता है), हालांकि मैं इसे तब तक काम करने की उम्मीद करता हूं जब तक कैटर्रैक्शन विधि को पहले कॉल किया जाता है संपत्ति परिवर्तन, एक गारंटी के रूप में एक एनीमेशन शुरू होने से पहले ब्लॉक को CATransaction को दिया जाता है।

20

allowsEdgeAntialiasingCALayer की संपत्ति की जांच करें।

block.layer.allowsEdgeAntialiasing = YES; // iOS7 and above. 
+1

बस ऊपर की तरह (Info.plist) लेकिन अधिक बारीक नियंत्रण! अति उत्कृष्ट! – horseshoe7

+1

स्वीकृत उत्तर इस तरह काम करता है, लेकिन यह बेहतर प्रदर्शन करता है। दोनों एक ही रैम खर्च करते हैं, लेकिन यह समाधान उपयोगकर्ता को उच्च एफपीएस प्रदान करता है। –

+0

इस संपत्ति के लिए प्रलेखन का कहना है कि यदि जानकारी Info.plist मान अनुपस्थित है तो मान नहीं है।जाहिर है, आप बस इस संपत्ति को सेट नहीं कर सकते हैं, लेकिन इसे प्लास्ट के साथ संयोजन में उपयोग करना होगा। मैंने परीक्षण नहीं किया है कि संपत्ति सेट नहीं होने पर क्या होता है, लेकिन AddisDev द्वारा उत्तर से निर्णय लेता है, यह उस मामले में हां तक ​​चूक जाता है। तो यदि कोई प्रदर्शन हिट होता है और आपको एंटीअलाइजिंग की आवश्यकता नहीं होती है, तो ऐसा लगता है कि यह मान NO को सेट करना है। –

संबंधित मुद्दे