2012-09-12 26 views
6

Tôi đang sử dụng hình ảnh để đặt làm nền cho tất cả hoạt động của mình nhưng nó đang gây ra sự cố tràn bộ nhớ và làm hỏng ứng dụng. Bây giờ tôi đang unbinding drawables của tôi trên pause() và trên Destroy() trong hoạt động của tôi và bây giờ nó cho thấy màn hình trống trên cách nhấn nút quay lại. Vì vậy, làm thế nào tôi có thể tránh điều này mà không cần sử dụng thêm bộ nhớ.Hủy liên kết drawables onPause() gây ra điều hướng ngược lại và bỏ qua bước này gây ra tràn bộ nhớ

protected void onPause(){ 
    super.onPause(); 
    unbindDrawables(findViewById(R.id.login_root)); 
} 

protected void onDestroy() { 
     unbindDrawables(findViewById(R.id.login_root)); 
     super.onDestroy(); 
     } 

private void unbindDrawables(View view) { 
    System.gc(); 
    Runtime.getRuntime().gc(); 
    if (view.getBackground() != null) { 
    view.getBackground().setCallback(null); 
    } 
    if (view instanceof ViewGroup) { 
     for (int i = 0; i < ((ViewGroup) view).getChildCount(); i++) { 
     unbindDrawables(((ViewGroup) view).getChildAt(i)); 
     } 
    ((ViewGroup) view).removeAllViews(); 
    } 

Ban đầu tôi đã thổi phồng bố trí của tôi sử dụng android: background = "@ drawable /" mà luôn luôn gây ra lỗi tràn bộ nhớ nói rằng VM sẽ không cho phép chúng ta phân bổ 10MB Bây giờ tôi nhận được một bitmap từ (ứng dụng). có thể drawable mà không co giãn và ràng buộc nó trên runtime.Now nó nói VM sẽ không cho phép chúng ta phân bổ 5MB (app.) mà không sử dụng unbindDrawables (..) Rõ ràng chất lượng của hình nền được hiển thị đã giảm nhưng tôi không thể để hiểu rằng nếu tôi đang sử dụng tệp png của 13KB, JVM yêu cầu không gian 5 hoặc 10MB để xử lý yêu cầu như thế nào?

Tôi đã thay đổi bố cục bố cục từ phương thức onCreate() sang phương thức onResume() nhưng ứng dụng lại hết bộ nhớ khi nhấn nút quay lại.

public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
    } 

    protected void onResume(){ 
     setContentView(R.layout.home); 
     Bitmap bmp; 
     ImageView background = (ImageView)findViewById(R.id.iv_home_background); 
     InputStream is = getResources().openRawResource(R.drawable.background); 
     bmp = BitmapFactory.decodeStream(is); 
     background.setImageBitmap(bmp); 

     super.onResume(); 
    } 

protected void onPause(){ 
     super.onPause(); 
     unbindDrawables(findViewById(R.id.home_root)); 
    } 


private void unbindDrawables(View view) { 
     System.gc(); 
     Runtime.getRuntime().gc(); 
     if (view.getBackground() != null) { 
     view.getBackground().setCallback(null); 
     } 
     if (view instanceof ViewGroup) { 
      for (int i = 0; i < ((ViewGroup) view).getChildCount(); i++) { 
      unbindDrawables(((ViewGroup) view).getChildAt(i)); 
      } 
     ((ViewGroup) view).removeAllViews(); 
     } 
    } 
+0

Hãy nhớ rằng nếu onDestroy() được gọi, onPause() cũng được gọi trước đó. –

+0

unbind chỉ trong 'onPause()' như @JohnSatriano đã nêu. Tuy nhiên, hãy chỉ cho chúng tôi chức năng onResume của bạn –

+0

Tôi đã không ghi đè lên chức năng Tiếp tục của tôi. Tôi hoàn toàn không biết phải làm gì ở đó. – Atinder

Trả lời

1

Tôi đã tìm được một công việc xung quanh cho vấn đề này. Bây giờ tôi đang chia tỷ lệ bitmap của tôi ở thời gian chạy thành một kích thước rất nhỏ và sau đó lưu trữ chúng trong bộ nhớ trong. Chương trình gọi các bitmap thu nhỏ từ bộ nhớ trong thời gian chạy và nếu nó không xuất hiện ở đó, nó gọi nó từ thư mục drawable, mở rộng nó, ghi nó vào bộ nhớ và sau đó liên kết nó với khung nhìn. Bằng cách này, không cần phải gọi phương thức unbindDrawables tại bất kỳ thời điểm nào và ứng dụng vẫn đáp ứng trong suốt. Mối quan tâm duy nhất của tôi bây giờ là chất lượng của ảnh bitmap, tôi nghĩ rằng tôi cần phải chơi xung quanh với kích thước mở rộng để tìm ra kích thước nhỏ nhất có thể với chất lượng tối đa.

0

Bạn đang gọi GC cho mỗi chế độ xem phụ. Hãy thử gọi nó chỉ một lần khi tất cả các unbinds được thực hiện.

unbindDrawables(findViewById(R.id.login_root)); 
System.gc(); 

GC là tải nặng và vô dụng khi gọi quá thường xuyên. trong thực tế, nếu không có rò rỉ, nó phải là nesesary ở tất cả.

Cũng nên nhớ rằng kích thước tệp png không liên quan gì đến bitmap trên bộ nhớ. Dưới đây là thông tin thêm về điều đó http://developer.android.com/training/displaying-bitmaps/index.html

Các vấn đề liên quan