안드로이드에서 이미지를 불러오는 방법은 다양하다.
더 있을 수도 있겠지만, 이번 글에서는 위의 6가지 방법에 대해서 정리를 해본다.
tartActivityForResult의 Deprecated로 인해 권장되는 방법
permission 획득 필요 없음
API 33 실행 시
API 28 실행 시
예시 코드
class ActivityResultAPIActivity : AppCompatActivity() {
private val binding: ActivityResultApiactivityBinding by lazy {
ActivityResultApiactivityBinding.inflate(layoutInflater)
}
// Activity Result 등록
private val getContent = registerForActivityResult(ActivityResultContracts.GetContent()) { uri: Uri? ->
uri?.let {
// Uri 이미지 view에 표시
binding.imageView.setImageURI(uri)
} ?: run {
Toast.makeText(this, "No image selected", Toast.LENGTH_SHORT).show()
}
}
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(binding.root)
binding.button.setOnClickListener {
// 갤러리 열기
getContent.launch("image/*")
}
}
}
이전부터 사용되던 방법으로 예제가 많고 모든 API 버전에서 사용이 가능하나, 현재는 Deprecated됨
permission 획득 필요 없음
API 33 실행 시
API 28 실행 시 : 선택할 수 있는 갤러리 앱이 없으면 앱 또는 액티비티가 죽는다.
예시 코드
class StartActivityForResultActivity : AppCompatActivity() {
private val binding: ActivityStartForResultBinding by lazy {
ActivityStartForResultBinding.inflate(layoutInflater)
}
private val PICK_IMAGE = 100
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(binding.root)
binding.button.setOnClickListener {
val gallery = Intent(Intent.ACTION_PICK, MediaStore.Images.Media.INTERNAL_CONTENT_URI)
startActivityForResult(gallery, PICK_IMAGE)
}
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if (resultCode == Activity.RESULT_OK && resultCode == PICK_IMAGE) {
binding.imageView.setImageURI(data?.data)
}
}
}
permission 획득 필요 없음
API 33 실행 시
API 28 실행 시 : 선택할 수 있는 갤러리 앱이 없으면 앱 또는 액티비티가 죽는다.
예시 코드
class ActionPickActivity : AppCompatActivity() {
private val binding: ActivityActionPickBinding by lazy {
ActivityActionPickBinding.inflate(layoutInflater)
}
private val PICK_IMAGE = 100
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(binding.root)
binding.button.setOnClickListener {
val gallery = Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI)
startActivityForResult(gallery, PICK_IMAGE)
}
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if (resultCode == Activity.RESULT_OK && requestCode == PICK_IMAGE) {
binding.imageView.setImageURI(data?.data)
}
}
}
permission 획득 필요 없음
API 33 실행 시
API 28 실행 시
예시 코드
class ActionOpenDocumentActivity : AppCompatActivity() {
private val binding: ActivityActionOpenDocumentBinding by lazy {
ActivityActionOpenDocumentBinding.inflate(layoutInflater)
}
private val PICK_IMAGE = 100
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(binding.root)
binding.button.setOnClickListener {
val intent = Intent(Intent.ACTION_OPEN_DOCUMENT)
intent.addCategory(Intent.CATEGORY_OPENABLE)
intent.type = "image/*"
startActivityForResult(intent, PICK_IMAGE)
}
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if (resultCode == Activity.RESULT_OK && requestCode == PICK_IMAGE) {
binding.imageView.setImageURI(data?.data)
}
}
}
permission 획득 필요 없음
API 33 실행 시
API 28 실행 시
예시 코드
class StorageAccessFrameworkActivity : AppCompatActivity() {
private val binding: ActivityStorageAccessFrameworkBinding by lazy {
ActivityStorageAccessFrameworkBinding.inflate(layoutInflater)
}
private val PICK_DIRECTORY = 101
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(binding.root)
binding.button.setOnClickListener {
val intent = Intent(Intent.ACTION_OPEN_DOCUMENT_TREE)
startActivityForResult(intent, PICK_DIRECTORY)
}
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if (resultCode == Activity.RESULT_OK && requestCode == PICK_DIRECTORY) {
val directoryUri = data?.data
directoryUri?.let {
val documentUri = DocumentsContract.buildDocumentUriUsingTree(it , DocumentsContract.getTreeDocumentId(it))
binding.imageView.setImageURI(documentUri)
}
}
}
}
permission 획득 필요
API 33 실행 시
API 28 실행 시 : 선택할 수 있는 갤러리 앱이 없으면 앱 또는 액티비티가 죽는다.
예시 코드
class MediaStoreAPIActivity : AppCompatActivity() {
private val binding: ActivityMediaStoreApiactivityBinding by lazy {
ActivityMediaStoreApiactivityBinding.inflate(layoutInflater)
}
private val REQUEST_CODE_PERMISSION = 200
private val REQUEST_CODE_IMAGE = 300
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(binding.root)
binding.button.setOnClickListener {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU) {
if (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_MEDIA_IMAGES) != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(this, arrayOf(Manifest.permission.READ_MEDIA_IMAGES), REQUEST_CODE_PERMISSION)
} else {
openImageSelector()
}
} else {
if (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(this, arrayOf(Manifest.permission.READ_EXTERNAL_STORAGE), REQUEST_CODE_PERMISSION)
} else {
openImageSelector()
}
}
}
}
private fun openImageSelector() {
val intent = Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI)
startActivityForResult(intent, REQUEST_CODE_IMAGE)
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if (resultCode == Activity.RESULT_OK && requestCode == REQUEST_CODE_IMAGE) {
binding.imageView.setImageURI(data?.data)
}
}
override fun onRequestPermissionsResult(
requestCode: Int,
permissions: Array<out String>,
grantResults: IntArray
) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
if (requestCode == REQUEST_CODE_PERMISSION) {
if ((grantResults.isNotEmpty() && grantResults[0] == PackageManager.PERMISSION_GRANTED)) {
openImageSelector()
} else {
Toast.makeText(this, "Permission denied", Toast.LENGTH_SHORT).show()
}
}
}
}
code repository
https://github.com/neoneoneo123/ImageSample
TIL-20240710