LISTORY

안드로이드 파일 추가 및 삭제 시, 미디어 스캐닝 본문

IT/안드로이드

안드로이드 파일 추가 및 삭제 시, 미디어 스캐닝

LiStoryTeller 2017. 7. 27. 16:05


Android에서 사진을 찍었는데 갤러리에 바로 사진이 보이지 않을 경우나 파일을 생성했는데 파일관리자에서 보이지 않을 경우가 존재합니다.



저같은 경우는 예전에 파일 관리자 어플리케이션을 개발하는데, 파일을 새로 생성해도 파일관리자에 반영이 되지 않아 당황한 적이 있었습니다.


이는 안드로이드의 미디어 라이브러리에 파일이 추가되지 않아서 발생하는 경우로, 이럴 때 안드로이드를 재부팅하거나 SD카드를 다시 장착하면 자체적으로 미디어 스캔을 실행하여 파일 처리의 결과가 반영됩니다.


하지만 파일을 추가하거나 삭제할 때마다 기기를 껐다 켰다 할 수는 없으니, 수동으로 안드로이드 미디어 스캔을 해줘야 할 것입니다.


일단, 미디어 스캔을 위해 하는 가장 간단한 방법은 Broadcast를 보내는 것입니다.


sendBroadcast(new Intent(Intent.ACTION_MEDIA_MOUNTED,Uri.parse("file://"+Environment.getExternalStorageDirectory())));


이는 원하는 경로에 있는 모든 파일들에 대해 미디어 스캔을 실행할 수 있습니다.


하지만 해당 방법은 성능저하의 문제 등으로 KitKat부터는 사용할 수 없습니다.






KitKat 이후의 버전



KitKat 이후의 버전에서도 파일 미디어 스캔을 하는 가장 간단한 방법은 Boradcast를 보내는 것입니다.


Intent intent = new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE);

intent.setData(Uri.fromFile(file);

sendBroadcast(intent);


이는 미디어 스캐너로 하여금 Uri에 대한 파일을 스캔하고 미디어 라이브러리에 파일을 추가하도록 해줍니다.






MediaScannerConnection 사용



Broadcast를 사용하는 것도 방법이지만 MediaScannerConnection의 scanFile()을 사용하여 미디어 스캔을 할 수 있습니다.


MediaScannerConnection.scanFile( getApplicationContext(),

new String[]{file.getAbsolutePath()},

null,

new OnscanCompletedListener(){

@Override

public void onScanCompleted(String path, Uri uri) {

Log.v("File scan", "file:" + path + "was scanned seccessfully");

}

});



scanFile()의 Parameter는 다음과 같습니다


                          • context : 어플리케이션의 context

                          • paths : 추가할 파일의 경로를 나타내는 문자열

                          • mimeTypes : 파일의 MIME 유형을 나타내는 문자열

                          • callback : 스캔이 완료될 경우 호출


OnScanCompletedListener 자체가 OnScanCompleted() 메소드를 구현해야 합니다. 


이 메소드는 매개변수로 파일이름과 uri를 가져옵니다.




또는 MediaScannerConnection의 인스턴스를 만들어 사용할 수 있습니다.


이는 미디어 스캔을 하는 복잡한 방법이지만 좀더 많은 제어를 할 수 있습니다.


MediaScannerConnectionClient를 implements 하여 스캐너를 구현할 경우, 미디어 스캔이 완료되었을 경우는 물론 MediaScannerConnection이 연결되었을 경우에도 callback method를 사용할 수 있습니다.


public class MediaScanner implements MediaScannerConnection.MediaScannerConnectionClient {

private MediaScannerConnection _msc;

private File _file;


public MediaScanner(Context context, File f) {

_file = f;

_msc = new MediaScannerConnection(context, this);

_msc.connect();

}


@Override

public void onMediaScannerConnected() {

_msc.scanFile(_file.getAbsolutePath(), null);

}


@Override

public void onScanCompleted(String path, Uri uri) {

_msc.disconnect();

}

}


이렇게 구현해 둘 경우, 파일을 스캔하고 싶을 때 다음과 같이 사용할 수 있습니다.


MediaScanner mediaScanner = new MediaScanner(getApplicationContext(), file);


하지만 이 방법은 연결을 설정하는데 조금 시간이 걸릴 수 있으므로


Broadcast를 이용하여 미디어 스캔하는 것을 권장합니다.





Comments