2011-06-13 24 views
7

मेरे आईओएस ऐप में, मैंने एक ऐसा दृश्य बनाया है जो ड्राइंग के दौरान वास्तविक समय में UIBezierPath का उपयोग करके उंगली से खींचा गया पथ प्रस्तुत करता है। दुर्भाग्यवश, मुझे प्रदर्शन समस्याएं आ रही हैं क्योंकि पथ लंबा हो जाता है (कई सौ शिखर) और जब भी दृश्य ताज़ा हो जाता है तो पूरे पथ को आकर्षित करने के लिए अव्यवहारिक हो जाता है।बढ़ते हुए UIView

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

मैं दृश्य से कुछ भी न निकालने, इसलिए मैं clearsContextBeforeDrawing सक्षम करने के लिए और केवल नवीनतम खंड हर बार drawRect: कहा जाता है आकर्षित करने की कोशिश की, लेकिन ऐसा लगता है वहाँ वास्तविक सबूत की एक बड़ी राशि ऑनलाइन सुझाव है कि इस संपत्ति नहीं करता 'है कुछ भी नहीं करते हैं और मैं इसे बिल्कुल भी काम नहीं कर सका।

ड्राइंग को गति देने का सबसे अच्छा तरीका क्या है?

जो मैंने पढ़ा है, ऐसा लगता है कि मेरा सबसे अच्छा विकल्प एक (ऑफस्क्रीन) बिटमैप संदर्भ में चित्रित कर रहा है, इसलिए मैं थोड़ा कम जोड़ सकता हूं और इसे स्क्रीन पर प्रदर्शित होने वाले ग्राफिक्स संदर्भ में कॉपी कर सकता हूं, लेकिन मैंने यह भी पढ़ा यह संदर्भ को आवंटित करने में अक्सर धीमा होता है और आरजीबीए को आरजीबी रूपांतरण के कारण स्क्रीन पर छवि को प्रस्तुत करने में आवश्यक होता है।

ऐसा लगता है कि मैं CALayer (या तो ऑफस्क्रीन बफर के साथ या बिना) में कुछ करने में सक्षम हो सकता हूं - यह मेरे लिए अस्पष्ट है कि परत पर ड्राइंग कैसे काम करता है और क्या यह मैंने देखा है कि किसी भी समस्या को बाधित करेगा । contents संपत्ति CGImageRef स्वीकार करती है; क्या मैं CGImage बना सकता हूं तो अद्यतन करें सबकुछ वापस किए बिना वृद्धिशील? साथ ही, क्या पूरी चीज को दोबारा बिना किसी कैलियर की सामग्री में जोड़ना संभव है?

किसी भी अंतर्दृष्टि की सराहना की जाएगी।


संपादित करें: इनाम के लिए, कैसे ठीक, छवि बफर प्रारंभ यह पर एक घन बेज़ियर पथ आकर्षित करने के लिए का एक उदाहरण प्रदान करते हैं और यह स्क्रीन उचित रूप से करने के लिए कॉपी करें। कृपया अपनी विधि का उपयोग करने का एक नोट बनाएं - मुझे नहीं पता कि CGBitmapContextCreate का उपयोग करना सबसे अच्छा तरीका है या यदि कुछ और है तो मुझे इसका उपयोग करना चाहिए।

+0

(I ' यदि संभव हो तो OpenGL ES से बचने के लिए, क्योंकि ऐसा लगता है कि कार्यान्वयन की जटिलता में काफी कुछ जोड़ता है, क्योंकि मुझे ओपनजीएल के बारे में कुछ भी पता नहीं है।) –

उत्तर

1

बेजियरपाथ अच्छे हैं क्योंकि वे वैक्टर हैं, इससे कोई फर्क नहीं पड़ता कि वे आपके विचार का समाधान करेंगे। हालांकि अगर आपको अपने विचार का आकार बदलने की आवश्यकता नहीं है तो हर बार सबकुछ की गणना करने की आवश्यकता नहीं है। बस अंतिम चाप/रेखा की गणना करें और इसे पिछले (ऑफस्क्रीन) बफर पर खींचें, जिससे प्रदर्शन में सुधार होना चाहिए।

मुझे याद है कि इस तरह की चीजें करना और प्रदर्शन इतना बड़ी समस्या नहीं थी कि मुझे आईफोन 3 जीएस में 12fps मिल गया। जो बुरा नहीं है। (मैं बेजियर पथ का उपयोग नहीं कर रहा था, वास्तव में मैं CGImageRefs और कच्चे आरजीबीए बफर का उपयोग करके कुछ छवि प्रसंस्करण कर रहा था जो इस दृष्टिकोण का सबसे महंगा हिस्सा होना चाहिए। बेजियरपाथ की केवल एक चाप/रेखा की गणना करना बहुत सस्ता है)

+1

धन्यवाद। क्या आप विस्तारित कर सकते हैं कि बफर कैसे सेट करें और इसे स्क्रीन पर कैसे कॉपी करें? (मैं आईओएस प्रोग्रामिंग और कोर ग्राफिक्स के लिए कुछ नया हूँ।) –