2011-12-14 2 views
0

자바를 사용하는 경우 메모리 누수 OOM의 원인 ... : P안드로이드 : 며칠 그렇게 부드럽게 난 단지 프로그램 한 setImageURI

내 응용 프로그램은 사용자가 제공해야 다른 "프로젝트"를 저장하는 SQLite 데이터베이스를 사용

텍스트, 사진 및 위치. 문제는 일부 프로젝트를 탐색 할 때 메모리가 부족할 때 예외가 발생한다는 것입니다.

myImage.setImageURI (Uri.parse (msavePicture));

다섯 번째 시간의 4 번째. DDMS를 사용하면 할당 된 메모리가 새로운 부하 당 약 0.2Mbyte 증가한다는 것을 알 수 있습니다. 문제를 검색하여 사용해 보았습니다.

myImage.setImageDrawable (null);

하지만 문제는 남아 있습니다. 나는 또한 내가) (.recycle를 사용할 수

myBitmap = BitmapFactory.decodeFile(msavePicture); 
    ImageView myImage = (ImageView) this.findViewById(R.id.camera_preview); 
    myImage.setImageBitmap(myBitmap); 

에 코드를 변경 시도했습니다; 하지만 그림이로드되면 null을 반환합니다. msavePicture은 다음과 같습니다 문자열입니다 :

파일 : ///mnt/sdcard/MyCameraApp/IMG_2011-12-09-01-49.jpg 내가

을 포함 시켰습니다

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/> 

매니페스트에서 나는 그림이 존재한다는 것을 알고 있기 때문에 setImageURI를 사용할 때 작동합니다.

그래서 질문입니다 : 메모리 누수가 발생하는 이유는 무엇입니까, 진정으로 ImageView를 파괴하는 방법, 또는 Bitmapfactory에서 내 문자열을 디코딩 할 수없는 이유는 파일 위치가 잘못 되었습니까?

나는 많은 경우 활동을 포함시켰다. 이것에 관한 어떤 해결책이나 링크도 크게 감사하겠습니다!

미리 감사드립니다.

(PS : 사람이 어떻게 당신이 다른 전화를 업데이트 할 수 있도록 서버에 SQLite 데이터베이스를 저장하는 가이드를 알고있는 경우도 크게 감사하겠습니다! =) : DS)

public class Page3 extends Activity { 
private static final int ACTIVITY_CREATE = 0; 
public static Long Row = (long) 40; 
public static String summarydec = "FAIL"; 
public static String msavePicture; 
public static Location loc; 
private EditText mgps_lati; 
private EditText mgps_long; 
static String gps_long; 
static String gps_lati; 
private TodoDbAdapter mDbHelper; 
public Location myLocation; 
public static Bitmap myBitmap; 
public Uri uBitmap; 


@Override 
protected void onCreate(Bundle bundle) { 
    super.onCreate(bundle); 
    mDbHelper = new TodoDbAdapter(this); 
    mDbHelper.open(); 
    setContentView(R.layout.camera); 


     if(msavePicture == null){ 
     msavePicture = ""; 
    } 
//  myBitmap = BitmapFactory.decodeFile(msavePicture); 
//  ImageView myImage = (ImageView) this.findViewById(R.id.camera_preview); 
//  myImage.setImageBitmap(myBitmap);  

    ImageView myImage = (ImageView) this.findViewById(R.id.camera_preview); 
    myImage.setImageURI(Uri.parse(msavePicture)); 

    mgps_long = (EditText) findViewById(R.id.gps_long); 
    mgps_lati = (EditText) findViewById(R.id.gps_lati); 
    mgps_lati.setText("Latitude: "+gps_lati); 
    mgps_long.setText("Longitude: "+gps_long); 
    //////////////////////////////////////////////////////////// 
    ///// G P S - L Y S S N A R E //////////////////////////// 
    ////////////////////////////////////////////////////////////  
    MyLocation myLocation = new MyLocation(); 
    myLocation.getLocation(this, locationResult); 

    Button gps = (Button) findViewById(R.id.gps); 
    gps.setOnClickListener(new View.OnClickListener() { 
     public void onClick(View view) { 

      if (gps_lati != null && gps_long != null) { 
       mgps_lati.setText("Latitude: " +gps_lati); 
       mgps_long.setText("Longitude: " +gps_long); 
       TodoDetails.save_gps_long = gps_long; 
       TodoDetails.save_gps_lati = gps_lati; 
       Page1.save_gps_long = gps_long; 
       Page1.save_gps_lati= gps_lati; 
       Page2.save_gps_long = gps_long; 
       Page2.save_gps_lati= gps_lati; 
       } else { 
        String Latitude = "Fel vid GPS-hanteringen, arra det!"; 
        String Longitude = "Fel vid GPS-hanteringen, arra det!"; 
        mgps_lati.setText(Latitude); 
        mgps_long.setText(Longitude); 
       } 
     }}); 
    //////////////////////////////////////////////////////////// 
    //////////////////////////////////////////////////////////// 

    Button camera = (Button) findViewById(R.id.camera); 
    camera.setOnClickListener(new View.OnClickListener() { 
     public void onClick(View view) {     
      createCamera(); 
     }}); 

    Button confirmButton = (Button) findViewById(R.id.todo_edit_button); 
    confirmButton.setOnClickListener(new View.OnClickListener() { 
     public void onClick(View view) {     
      setResult(RESULT_OK); 
      TodoDetails.mPIC = msavePicture; 
      Page1.mPIC = msavePicture; 
      Page2.mPIC = msavePicture; 
      ImageView myImage = (ImageView) findViewById(R.id.camera_preview); 
      myImage.setImageDrawable(null); 
//    myBitmap.recycle(); 
      cancelTimer(); 
      finish(); 
     } 

    }); 
} 
protected void onPause() { 
    super.onPause(); 
    cancelTimer(); 
    ImageView myImage = (ImageView) findViewById(R.id.camera_preview); 
    myImage.setImageDrawable(null); 

} 
protected void cancelTimer() 
{ 
    MyLocation myLocation = new MyLocation(); 
    myLocation.cancelTimer(); 
} 
protected void onActivityResult(int requestCode, int resultCode, 
     Intent intent) { 
    super.onActivityResult(requestCode, resultCode, intent); 
    cancelTimer(); 
    ImageView myImage = (ImageView) findViewById(R.id.camera_preview); 
    myImage.setImageURI(Uri.parse(msavePicture)); 

//  ImageView myImage = (ImageView) this.findViewById(R.id.camera_preview); 
//  myBitmap = BitmapFactory.decodeFile(msavePicture); 
//  myImage.setImageBitmap(myBitmap); 

} 
public void onBackPressed(){ 
    cancelTimer(); 
    ImageView myImage = (ImageView) findViewById(R.id.camera_preview); 
    myImage.setImageDrawable(null); 
//  Bitmap myBitmap = Page3.myBitmap; 
//  myBitmap.recycle(); 
    finish(); 
} 
//////////////////////////////////////////////////// 
////////////// A L L A V Y E R /////////////////// 
//////////////////////////////////////////////////// 
private void createPage1() { 
    Intent b = new Intent(this, Page1.class); 
    startActivityForResult(b, ACTIVITY_CREATE); 
    setResult(RESULT_OK, b); 
    finish(); 
} 
private void createPage2() { 
    Intent b = new Intent(this, Page2.class); 
    startActivityForResult(b, ACTIVITY_CREATE); 
    setResult(RESULT_OK, b); 
} 
private void createTodo() { 
    Intent i = new Intent(this, TodoDetails.class); 
    startActivityForResult(i, ACTIVITY_CREATE); 
    setResult(RESULT_OK, i); 
} 
private void createCamera() { 
    Intent c = new Intent(this, Camera.class); 
    startActivityForResult(c, ACTIVITY_CREATE); 
    setResult(RESULT_OK, c); 
} 
////////////////////////////////////////////////////////// 
//////// M E N U T O O L B A R ////////////////////////// 
@Override 
public boolean onCreateOptionsMenu(Menu menu) { 
    MenuInflater inflater = getMenuInflater(); 
    inflater.inflate(R.menu.projektlist, menu); 
    return true; 
} 
public LocationResult locationResult = new LocationResult(){ 
    @Override 
    public void gotLocation(final Location location){ 
     gps_lati = Double.toString(location.getLatitude()); 
     gps_long = Double.toString(location.getLongitude()); 
     }}; 
} 

답변

0

당신은 다운 스케일한다 ImageView 크기의 비트 맵. 예 :

int ratio = widhtOriginal/widthImageView; 
// Just an example, you should use more sophisticated algorithm 

BitmapFactory.Options options = new BitmapFactory.Options(); 
options.inSampleSize = ratio; 

InputStream inputStream = context.getContentResolver().openInputStream(uri); 
// Will work for Uri's with "content" scheme, 
// otherwise use BitmapFactory.decodeFile(String, Options) and so on 

Bitmap bitmap = BitmapFactory.decodeStream(inputStream, null, options); 
+0

예제 코드를 구현하는 데 어려움이 있습니다. 주어진 소스에있는 파일을 열 수있는 Uri.parse (msavePicture)를 시도해 보았습니다. 앞서 언급 한 것처럼 BitmapFactory.decodeFile은 null을 반환합니다. 보기에 맞게 사진의 크기를 조정해야합니까? 지나치게 복잡하게 들립니다. 시도해 줘서 고마워, 내가 오해 한 것이 있으면 알려줘 ..! – user1097221

+0

OOM을 피하려면 정말 필요합니다. 같은 문제가 발생하고 축소하면 도움이되었습니다. InputStream을 열 때 Uri에 정의 된 스키마를 구별해야합니다. [구현 방법] (http://grepcode.com/file/repository.grepcode.com/java/ext/com.google.android/android/1.5_r4/android/widget/ImageView.java#ImageView를 참조하십시오.resolveUri())를 ImageView에 저장하고 앱에 맞게 수정하십시오. –

관련 문제