2012-09-29 12 views
24

अगर कोई यह पुष्टि कर सकता है कि मैंने नीचे दी गई समस्या को सही तरीके से हल किया है या यदि कोई वैकल्पिक समाधान है तो मैं बहुत आभारी हूं?एंड्रॉइड बिटमैप मेमोरी त्रुटि से बाहर लोड हो रहा है गैलेक्सी एस 3 डब्ल्यूएक्सजीए

मेरे पास एक ऐप है जो एक बड़ी छवि (उदाहरण के लिए 800 * 1720 पिक्सल) को स्मृति में लोड करता है और इसे स्क्रॉलव्यू में प्रदर्शित करता है। छवि एक संग्रहालय के लिए एक मंजिल योजना है और मैं स्क्रॉलिंग और ज़ूमिंग के अनुभव जैसे एक साधारण मानचित्र चाहता था। छवि पुराने उपकरणों पर ठीक से लोड हो गई, लेकिन सैमसंग गैलेक्सी एस 3 पर मेमोरी त्रुटि से बाहर निकला।

लॉगकैट संदेशों को देखते हुए यह पता चला कि बिटमैप 22 एमबी को क्रिएट करने में 800 * 1720 * 4 = 5.5 एमबी के बजाय बिटमैप के लिए आवंटित किया जा रहा था। अनिवार्य रूप से 4x जितनी अधिक स्मृति आवंटित की जा रही थी, अन्य उपकरणों द्वारा आवश्यक और 50 एमबी ढेर आकार पर स्मृति उपयोग को धक्का दे रहा था।

इस समस्या का अनुशंसित समाधान BitmapFactory.Options.inSampleSize विकल्प का उपयोग छवि के संकल्प को कम करने के लिए किया गया है और इसे कम स्मृति की आवश्यकता है। हालांकि, यह छवि की गुणवत्ता को कम कर देता है, और मैं वास्तव में इसे मूल गुणवत्ता में पूर्ण आकार में प्रदर्शित करना चाहता हूं क्योंकि पुराने उपकरणों पर ठीक काम करता है।

अधिक सिर स्क्रैचिंग के बाद मैंने निष्कर्ष निकाला कि मुद्दा यह था कि एस 3 की डब्ल्यूएक्सजीए स्क्रीन पर पिक्सेल घनत्व 2.0 है और इस प्रकार छवि में प्रत्येक पिक्सेल के लिए, बिटमैप वास्तव में 4 पिक्सल आवंटित कर रहा था। परीक्षण और त्रुटि का एक सा के साथ मुझे पता चला मैं रास्ते में options.inScaled = false;

http://developer.android.com/reference/android/graphics/BitmapFactory.Options.html#inScaled

की स्थापना द्वारा हो रहा रोक सकता है, मैं भी एहसास हुआ कि मैं एक कम निष्ठा का उपयोग करके 2.7MB को छमाही में मेरी स्मृति के उपयोग में कटौती कर सकता है options.inPreferredConfig = Bitmap.Config.RGB_565; सेट करके 4 पिक्सेल की बजाय 2 पिक्सल की रंग गहराई। मेरे फर्शपैन के लिए यह दृश्य छवि गुणवत्ता को प्रभावित नहीं करता है।

अंतिम कोड इस प्रकार था:

String uri = "drawable/floorplan"; 
int imageResource = getResources().getIdentifier(uri, null, getPackageName()); 
BitmapFactory.Options options = new BitmapFactory.Options(); 
options.inPreferredConfig = Bitmap.Config.RGB_565; 
options.inScaled = false; 
Bitmap bm = BitmapFactory.decodeResource(getResources(), imageResource, options); 
IVfloorplan.setImageBitmap(bm); 

जब यह बिटमैप आप इसे पैमाने पर वापस ऊपर की जरूरत प्रदर्शित। स्केलिंग बाहर काम करने के लिए आप से पिक्सेल घनत्व प्राप्त कर सकते हैं:

float density = getResources().getDisplayMetrics().density; 

मैं 2.7MB को 22MB से बिटमैप है, जो एक 50MB ढेर में महत्वपूर्ण है के लिए स्मृति उपयोग कम कर दिया।

+3

में बिटमैप ऑब्जेक्ट्स का उपयोग करते समय ढेर स्पेस से बाहर निकलना बहुत आसान है और समाधान के लिए धन्यवाद। – Simon

+0

मुझे लगता है कि यहां प्रलेखन लिंक प्रदान करना अच्छा हो सकता है जो आंशिक रूप से केवल नमूना आकार के बारे में बताता है: http://developer.android.com/training/displaying-bitmaps/load-bitmap.html। और http://www.curious-creature.org/2010/12/08/bitmap-quality-banding-and-dithering/ बिटमैप रंग प्रारूपों और उसके प्रोप/विपक्ष के साथ खेलने के बारे में। – sandrstar

+0

कमाल। मुझे लगता है कि इससे कम ढेर आकार वाले अन्य उपकरणों के लिए भी मदद मिलेगी .. लेकिन आपको अपने प्रश्न में इसका जवाब देने के बजाय एक जवाब जोड़ना चाहिए, क्योंकि यह एसओ नियमों का उल्लंघन करता है और प्रश्न को हटाए जाने से सुरक्षित बना देता है। –

उत्तर

2

एस 3 की स्क्रीन में वास्तव में उच्च रेज है, इसलिए यह काफी समझ में आता है। साथ ही, यदि छवि खींचने योग्य फ़ोल्डर में है, तो यह स्वचालित रूप से upscaled हो सकता है। इसे बंद करने के तरीके हो सकते हैं। यहां तक ​​कि यदि आपकी छवि आकार का मौका नहीं है, तो ओएस को छवि को समायोजित करने के लिए एक बफर आवंटित करना होगा, संभवतः स्क्रीन पर इसे दिखाने के लिए भी एक को।

एक विकल्प टाइलिंग का उपयोग कर रहा है, जिसका उपयोग एसएनईएस गेम्स जैसे गेम में किया जाता है। यह भी है कि उन्होंने रैम से बाहर किए बिना बहुत सारे ग्राफिक्स को कैसे संभाला। साक्ष्य दर्शाते हैं कि इस प्रकार Google मानचित्र के पास ग्रह पृथ्वी का नक्शा है। आप मूल रूप से बड़ी छवि को टाइल्स में काटते हैं और स्क्रीन पर टाइल दिखाते हैं क्योंकि आप उन्हें पॅन कर रहे हैं (बेशक, शायद प्रत्येक तरफ 1 अतिरिक्त टाइल)।

भले ही यह हनीकॉम है, जहां Google बिटमैप आवंटन को बेहतर तरीके से प्रबंधित करने के लिए कोड में डालता है, बिटमैप आवंटन से सावधान रहें। यह जावा प्रोग्राम की तुलना में सी प्रोग्राम की तरह है, और इसे एक जैसे प्रबंधित करना एक अच्छा विचार है। Android