안드로이드 스튜디오를 통한 애플리케이션 제작을 위해서는 여러 가지 기능을 이용해야 합니다.
그중, 권한 설정과 관련된 내용을 일반화해볼까 합니다.
제일 먼저 해야 할 일은 Manifests에 권한들을 추가해주어야 하는 것인데, 그것은 맨 마지막으로 떼고 먼저 자바 코드 먼저 작성해보겠습니다.
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
//퍼미션 상태 확인
if (!hasPermissions(PERMISSIONS)) {
//퍼미션 허가 안되어있다면 사용자에게 요청
requestPermissions(PERMISSIONS, PERMISSIONS_REQUEST_CODE);
}else{
Intent intent = new Intent(this, RunningActivity.class); //실행 화면
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(intent);
finish();
}
}
제일 먼저 해야 할 일은 현재 어플을 사용할 안드로이드 폰의 버전이 마시멜로우 버전 이상인지 확인해야 합니다. 만약 그것보다 낮은 api(23)라면 Manifests에 설정해주는 것 만으로 권한 설정을 해 줄 수가 있습니다.
하지만 현재 사용하는 스마트폰은 아마 대부분이 api 업데이트가 최신에 가까울 테니, 그에 대한 고려 역시 필수적입니다. 그 문제는 코드의 첫 줄의 if 안의 문장으로 해결이 가능합니다.
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M)
이 조건은 스마트폰의 SDK 버전이 마시멜로우의 버전보다 높거나 같은지를 확인하는 부분입니다.
if (!hasPermissions(PERMISSIONS))
{
//퍼미션 허가 안되어있다면 사용자에게 요청
requestPermissions(PERMISSIONS, PERMISSIONS_REQUEST_CODE);
}
else
{
Intent intent = new Intent(this, RunningActivity.class); //실행 화면
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(intent);
finish();
}
그 다음은 권한 설정을 사용자에게 이미 받은 상태인지 확인하는 부분입니다. 사실 권한 요청은 필수적이지만 한 번 하고 나면 사용자가 다시 일부러 해제하기 전까지는 유지되는 부분입니다.
그리고 여기서 대문자로 된 PERMISSIONS에는 자신이 넣어줄 퍼미션을 배열에다가 넣어주면 됩니다. 쉽게 이해할 수 있도록 가장 자주 쓰는 권한들을 넣어두었습니다.
PERMISSIONS_REQUEST_CODE는 onRequestPermissionsResult()가 콜백되었을 때, 파라미터로 사용됩니다. 이를 이용하면 각 권한마다 다른 메시지를 포함할 수도 있고 다른 행동을 취할 수도 있습니다. 현재 작성한 코드는 간편하게 보여주기 위해 모두 동일한 작업을 시행하게 됩니다.
static final int PERMISSIONS_REQUEST_CODE = 1000;
String[] PERMISSIONS = {Manifest.permission.CAMERA,
Manifest.permission.WRITE_EXTERNAL_STORAGE,
Manifest.permission.INTERNET};
hasePermissions의 경우는 아래에 서술할 메소드로, 자체로 만든 코드입니다.
private boolean hasPermissions(String[] permissions)
{
int result;
//스트링 배열에 있는 퍼미션들의 허가 상태 여부 확인
for (String perms : permissions)
{
result = ContextCompat.checkSelfPermission(this, perms);
if (result == PackageManager.PERMISSION_DENIED){
//허가 안된 퍼미션 발견
return false;
}
}
//모든 퍼미션이 허가되었음
return true;
}
permissions라는 변수에 필요한 퍼미션을 넣어두고, 반복문을 통해 여러개의 퍼미션의 권한 체크 여부를 확인하는 코드입니다. ContextCompat.checkSelfPermission은 파라미터로 받은 퍼미션을 확인해 결과값을 리턴해주는데, 이는 PackagerManager.~을 통해 확인할 수 있습니다. 여기서 권한 확인이 되는 경우에 else문으로 들어가 실제 애플리케이션의 메인이 되는 액티비티를 불러오게 할 수 있습니다.
물론 ContextCompat.checkSelfPermission을 실행시키면 shouldShowRequestPermissionrationale()을 콜백해줍니다. 이 메소드를 오버라이딩해서 팝업창을 커스텀하거나 요청 창에서 메시지를 커스텀할 수도 있습니다.
이후, 권한이 없다면 당연히 권한을 요청해줘야 할 것이고, 그것이 조건문 안에 나오는 requestPermissions 메소드 입니다. 이 메소드는 onRequestPermissionsResult()를 콜백해줍니다. 이 메소드를 오버라이딩해야 원하는 권한들을 줄 수 있습니다.
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions,
@NonNull int[] grantResults)
{
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
switch(requestCode)
{
case PERMISSIONS_REQUEST_CODE:
if (grantResults.length > 0)
{
boolean cameraPermissionAccepted = grantResults[0] == PackageManager.PERMISSION_GRANTED;
boolean diskPermissionAccepted = grantResults[1] == PackageManager.PERMISSION_GRANTED;
boolean internetPermissionAccepted = grantResults[2] == PackageManager.PERMISSION_GRANTED;
if (!cameraPermissionAccepted || !diskPermissionAccepted || !internetPermissionAccepted)
permissionDialog("앱을 실행하려면 퍼미션을 허가하셔야합니다.");
else
{
Intent intent = new Intent(this, RunningActivity.class);
startActivity(intent);
finish();
}
}
break;
}
}
이 메소드가 콜백되었다면 권한의 GRANTED인지 DENIED인지 확인할 수 있는 grantResults라는 정수형 배열이 파라미터로 들어오게 됩니다. 이를 boolean 타입을 통해 저장합니다. 이를 조건문에서 확인해 하나라도 디나이된 것이 있다면 permissionDialog 이라는 메소드를 통해 다이얼로그를 띄워주게 됩니다.
@TargetApi(Build.VERSION_CODES.M)
private void permissionDialog(String msg)
{
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setTitle("권한 설정");
builder.setMessage(msg);
builder.setCancelable(false);
builder.setPositiveButton("예", new DialogInterface.OnClickListener()
{
public void onClick(DialogInterface dialog, int id)
{
requestPermissions(PERMISSIONS, PERMISSIONS_REQUEST_CODE);
}
});
builder.setNegativeButton("아니오", new DialogInterface.OnClickListener()
{
public void onClick(DialogInterface arg0, int arg1)
{
finish();
}
});
builder.create().show();
}
이 메소드는 메시지를 파라미터로 받아서 타이틀과 메시지를 설정하고 예를 누를 경우 requestPermissions를 재실행함으로서 권한 설정을 위한 팝업창을 다시 띄워 권한을 주고 아니요를 누를 경우 그대로 액티비티가 종료되게 선언해두었습니다. 이는 이 창을 맨 처음 실행할 경우에는 애플리케이션이 종료가 되는 형태로 이루어집니다.
이렇게 설정을 했다면 액티비티에서 권한을 주는 기능이 완료되었습니다.
이제 마지막으로 Manifests에 권한을 추가할 차례입니다.
<uses-permission android:name="android.permission.CAMERA"/>
<uses-permission android:name="android.permission.INTERNET"/>
이와 같이 Manifests 내부에 권한을 주고 싶은 것들을 작성해주시면 됩니다.
이로서 권한 설정이 완료되었습니다. 이 아래로는 권한의 종류에 대해서 적어놓았습니다.
ACCESS_CHECKIN_PROPERTIES 체크인데이터베이스의_속성테이블로_액세스
ACCESS_COARSE_LOCATION 코스_로케이션_액세스_(Cell-ID/WiFi)
ACCESS_FINE_LOCATION 파인로케이션_액세스(GPS)
ACCESS_LOCATION_EXTRA_COMMANDS 로케이션_옵션_커맨드_액세스
ACCESS_MOCK_LOCATION 목_로케이션_프로바이더_생성_(테스트용)
ACCESS_NETWORK_STATE 네트워크_상태_접근
ACCESS_SURFACE_FLINGER 서피스_플링거_접근
ACCESS_WIFI_STATE WiFi상태_접근
ADD_SYSTEM_SERVICE 시스템서비스_추가
BATTERY_STATS 배터리_상태
BLUETOOTH 블루투스
BLUETOOTH_ADMIN 블루투스_어드민
BRICK 디바이스_실효성_지정
BROADCAST_PACKAGE_REMOVED 제거된_패키지에_대한_notification_브로드캐스트
BROADCAST_SMS SMS에_대한_브로드캐스트
BROADCAST_STICKY 인텐트_브로드캐스트
CALL_PHONE 통화
CALL_PRIVILEGED 통화(긴급전화_포함)
CAMERA 카메라
CHANGE_COMPONENT_ENABLED_STATE 컴포넌트의_실효성_변경
CHANGE_CONFIGURATION 컨피그_변경
CHANGE_NETWORK_STATE 통신상태_변경
CHANGE_WIFI_STATE WiFi상태_변경
CLEAR_APP_CACHE 어플리케이션_캐시_클리어
CLEAR_APP_USER_DATA 어플리케이션의_유저데이터_클리어
CONTROL_LOCATION_UPDATES 위치정보_갱신
DELETE_CACHE_FILES 캐시파일_제거
DELETE_PACKAGES 패키지_제거
DEVICE_POWER 전원상태에_대한_로우레벨_접근
DIAGNOSTIC 진단리소스_읽고쓰기
DISABLE_KEYGUARD 키_가드_끄기_DUMP_덤?
EXPAND_STATUS_BAR 상태표시줄_확장
FACTORY_TEST 팩토리_테스트
FLASHLIGHT 플래시라이트
FORCE_BACK 포스백
GET_ACCOUNTS 어카운트_획득
GET_PACKAGE_SIZE 패키지_획득
GET_TASKS 태스크_획득
HARDWARE_TEST 하드웨어테스트
INJECT_EVENTS 유저이벤트_키/트랙볼
INSTALL_PACKAGES 패키지_인스톨
INTERNAL_SYSTEM_WINDOW 내부_시스템윈도_활용
INTERNET 인터넷
MANAGE_APP_TOKENS 어플리케이션_토큰관리
MASTER_CLEAR 마스터_클리어
MODIFY_AUDIO_SETTINGS 오디오설정_편집
MODIFY_PHONE_STATE 전화상태_편집
MOUNT_UNMOUNT_FILESYSTEMS 파일시스템_편집
PERSISTENT_ACTIVITY 액티비티_지속
PROCESS_OUTGOING_CALLS 전화_발신처리_접근
READ_CALENDAR 캘린더_읽어오기
READ_CONTACTS 주소록_읽어오기
READ_FRAME_BUFFER 프레임버퍼_읽어오기
READ_INPUT_STATE 입력상태_읽어오기
READ_LOGS 로그_읽어오기
READ_OWNER_DATA owner_data읽어오기
READ_PHONE_STATE 통화상태_읽어오기_READ_SMS_SMS읽어오기
READ_SYNC_SETTINGS 동기설정_읽어오기
READ_SYNC_STATS 동기상태_읽어오기
REBOOT reboot
RECEIVE_BOOT_COMPLETED boot완료
RECEIVE_MMS MMS수신
RECEIVE_SMS SMS수신
RECEIVE_WAP_PUSH WAP수신
RECORD_AUDIO 오디오_수신
REORDER_TASKS 태스크_Z오더
RESTART_PACKAGES 패키지_리스타트
SEND_SMS SMS송신
SET_ACTIVITY_WATCHER 액티비티_왓쳐지정
SET_ALWAYS_FINISH 액티비티_전체_종료
SET_ANIMATION_SCALE 스케일_애니메이션_지정
SET_DEBUG_APP 디버그어플리케이션_지정
SET_ORIENTATION 스크린_로테이션지정
SET_PREFERRED_APPLICATIONS 자주_사용하는_어플리케이션_지정
SET_PROCESS_FOREGROUND 포어그라운드_처리지정
SET_PROCESS_LIMIT 제한처리_지정
SET_TIME_ZONE 타임존_지정
SET_WALLPAPER 배경화면_지정
SET_WALLPAPER_HINTS 배경화면_힌트_지정
SIGNAL_PERSISTENT_PROCESSES 지속처리_시그널_지정
STATUS_BAR 상태표시줄_지정
SUBSCRIBED_FEEDS_READ 서브스트립드_피즈_읽어오기
SUBSCRIBED_FEEDS_WRITE 서브스트립드_피즈_쓰기
SYSTEM_ALERT_WINDOW 알림_윈도우
VIBRATE 진동
WAKE_LOCK 알람
WRITE_APN_SETTINGS APN설정_쓰기
WRITE_CALENDAR 캘린더_쓰기
WRITE_CONTACTS 주소록_쓰기
WRITE_GSERVICES G서비스_쓰기
WRITE_OWNER_DATA owner_data쓰기
WRITE_SETTINGS 설정_쓰기
WRITE_SMS SMS쓰기
WRITE_SYNC_SETTINGS 동기설정_쓰기
'안드로이드 > 자바' 카테고리의 다른 글
requireContext() vs getContext() (0) | 2022.05.10 |
---|---|
자바의 스트림에 대하여(2) - java 8 (0) | 2021.10.05 |
자바의 스트림에 대하여(1) - java 8 (0) | 2021.09.27 |
자바의 인터페이스란? (0) | 2021.08.10 |
(java) StringBuilder vs StringBuffer (0) | 2021.08.01 |
댓글