2023.03.02 - 안드로이드 앱개발자 과정

CHA·2023년 3월 3일
0

Android



Notification

Notification 이란 무엇일까?


Notification 동적 퍼미션

안드로이드의 13버전 (API 33) 부터 알림에 대한 동적 퍼미션이 추가되었습니다. 메니페스트 파일에 아래 코드를 작성합시다.

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

위 코드 처럼 퍼미션을 허용한다고 작성만 해놓으면 정적 퍼미션이 됩니다. 그래서 사용자가 앱을 사용할 때에는 물어보지 않으며, 다운로드 할 때에 어떤 기능을 이 앱에서 사용할지를 알려주게 됩니다. 인터넷 기능의 경우는 정적 퍼미션으로만 처리를 해주면 되지만, 위치 기반 서비스 혹은 카메라 기능 등은 중요한 퍼미션에 속하기때문에 사용자에게 동적으로 퍼미션을 요구해야 합니다.

즉, 다운로드 시 뿐 아니라, 앱을 사용할 때에도 사용자에게 퍼미션에 관한 확답을 받아내야 합니다. 그래서 다이얼로그를 이용하여 사용자로부터 퍼미션을 허용할건지의 여부를 물어야 합니다. 그리고 그에 대한 코드는 자바 코드로 작성해주어야 합니다.

그러면 이제 동적 퍼미션을 받을 다이얼로그를 만들러 가봅시다.

다이얼로그 생성하기

아래 코드의 clickBtn() 은 버튼을 클릭했을 때 퍼미션 허용 여부 다이얼로그가 뜨게 만들어 주는 기능이며, 나머지 코드는 아래 설명에서 알아봅시다.

 void clickBtn(){
        int checkResult = ContextCompat.checkSelfPermission(this, Manifest.permission.POST_NOTIFICATIONS);

        if(checkResult == PackageManager.PERMISSION_DENIED){
 			permissionResultLauncher.launch(Manifest.permission.POST_NOTIFICATIONS);
        }
    }

    ActivityResultLauncher<String> permissionResultLauncher = registerForActivityResult(new ActivityResultContracts.RequestPermission(),
    result -> {
       if(result) Toast.makeText(MainActivity.this, "알림 허용", Toast.LENGTH_SHORT).show();
       else Toast.makeText(MainActivity.this, "알림 허용하지 않음", Toast.LENGTH_SHORT).show();
    });
  • int checkResult = ContextCompat.checkSelfPermission(this, Manifest.permission.POST_NOTIFICATIONS);

    우리는 동적 퍼미션을 만들기 위해 Notification 에 대한 퍼미션을 허용한 상태인지를 먼저 체크해보아야 합니다. 이게 동적 퍼미션의 다이얼로그를 만들기 위한 시작입니다. 위 코드가 퍼미션 확인 코드 입니다. checkSelfPermission() 은 API 26 버전 이후에 나온 기능이므로, 하위 버전에서는 동작하지 않습니다. 그래서 Context 의 하위 호환용으로 만들어진 ContextCompat 을 이용합시다.
    첫번째 파라미터로는 Context 객체를, 두번째 파라미터로는 우리가 확인하고자 하는 퍼미션을 전달해야합니다. Manifest.permission.POST_NOTIFICATIONS 을 이용하면 Notification 에 대한 퍼미션 허용 정보를 전달해줄 수 있습니다.

    또한 checkSelfPermission() 의 반환형은 int 타입 이므로 int 형 변수 checkResult 에 반환값을 넣어주었습니다. 그리고 그 값이 0이라면 퍼미션이 허용되었다는것이며 아니라면 허용이 되지 않았다는 의미 입니다. 우리는 숫자만으로는 어떤 의미인지 파악하기 힘드니, Manifest 의 permission 참조변수를 이용하여 알맞은 값을 찾아줄 수 있습니다.

  • checkResult == PackageManager.PERMISSION_DENIED
    이제 우리는 퍼미션의 허용 여부를 값으로 받았으니, 알림이 허용되지 않았다면! 알림 허용을 요청해야 합니다. 요청을 해주어야 Notification 을 사용할수 있으니까요. 그래서 우리가 받아온 퍼미션의 허용 여부인 checkResultPERMISSION_DENIED 라면, 그러니까 알림이 허용되지 않았다면, 알림 허용을 요청하는 다이얼로그를 띄워주어야 합니다. 그리고 이 다이얼로그는 대행사를 통해 처리해줄 수 있습니다.

  • permissionResultLauncher.launch(Manifest.permission.POST_NOTIFICATIONS);
    ActivityResultLauncher 의 참조변수 permissionResultLauncher 를 이용하여 퍼미션의 요청결과를 받아올 수 있습니다. 대행사 ActivityResultLauncher 를 만드는 법은 액티비티의 화면전환때 했던 방식과 동일합니다. 다만, 액티비티 전환시에는 제네릭타입으로 Intent 를 주었지만, 이번에는 퍼미션을 처리해주어야 하므로 String 을 제네릭 타입으로 설정하였습니다. 또한 액티비티 전환시에는 계약 종류를 startActivityForResult 로 설정했지만, 이번에는 RequestPermission를 설정해주었습니다. 여기까지 하면, Notification 의 퍼미션 허용이 가능해집니다.

Notification 생성하기

void clickBtn(){

		... 중략 
        
        NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);

        NotificationCompat.Builder builder = null;

        if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.O){
            NotificationChannel channel = new NotificationChannel("ch01","Ex58 channel",NotificationManager.IMPORTANCE_HIGH);

            notificationManager.createNotificationChannel(channel);

            builder = new NotificationCompat.Builder(this,"ch01");
        }else {
            builder = new NotificationCompat.Builder(this,"");
        }
        Notification notification = builder.build();
        notificationManager.notify(100,notification);
    }
    
    
    
  • NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
    이제 Notification 을 관리하는 관리자 객체를 소환해봅시다. getSystemService() 을 이용하면 Notification 의 관리자 객체를 가져올 수 있습니다.getSystemService() 은 Context 의 스머프들을 불러올 수 있는 메소드 입니다. Resource 등은 너무 많이 사용되기 때문에 getResource() 와 같은 전용 메소드가 있는것일 뿐, 기본적으로는 getSystemService() 을 이용하여 Context 의 객체를 불러와야 합니다.

  • NotificationCompat.Builder builder = null;
    Notification 을 생성하기 위해서는 Builder 객체의 힘이 필요하므로, Builder 객체의 참조변수를 설정합시다. 그런데, 이 빌더를 생성하는 문법이 API 26 버전부터 변경되었습니다. 이 빌더를 생성하기 위해 알림채널이라는 개념이 도입되었는데, 그래서 26버전 이후라면 채널을 생성해주어야 하며, 이전 버전이라면 채널을 생성할 필요는 없습니다. 그래서 if 문을 활용하여 사용자의 버전값을 가져오고, 26버전 이상인지 이하인지를 판별하여 코드를 짜주어야 합니다.

  • Build.VERSION.SDK_INT >= Build.VERSION_CODES.O
    Build.VERSION.SDK_INT 은 사용자 기기의 버전 정보 입니다. Build.VERSION_CODES.O 은 안드로이드 버전 정보이며, O 는 Oreo 버전임을 뜻합니다. 즉, 사용자 기기의 버전정보가 오레오 버전 이상이라면~ 이라는 if 문의 조건으로 쓰였습니다.

  • NotificationChannel channel = new NotificationChannel("ch01","Ex58 channel",NotificationManager.IMPORTANCE_HIGH);
    if 문 안쪽이라면, 사용자 기기의 버전정보가 26버전 이상이므로, 빌더 객체를 생성하기 위해 채널 객체를 만들어주어야 합니다. 첫번째 파라미터로는 채널의 id 값을 지정해줄 수있고, 두번째는 채널의 이름, 세번째로는 중요도를 설정할 수 있습니다. 이 중요도는 Notification 이 띄워질 때, 중요도에 따라 소리가 날수도있고, 화면을 가리면서 띄워질수도 있습니다. 적절하게 설정해주면 될것같습니다.

  • notificationManager.createNotificationChannel(channel);
    Notification 매니저 객체에게 Builder 객체를 만들기 위한 채널을 만들어 달라고 요청합시다.

  • builder = new NotificationCompat.Builder(this,"ch01");
    이제 Builder 객체를 만들어봅시다. 파라미터로는 Context 객체 하나와 채널의 id 값을 전달해주어야 합니다.

  • builder = new NotificationCompat.Builder(this,"");
    API 26 버전 이전 또한 builder 를 생성해줄 수 있습니다. 다만, channel 의 개념은 없기 때문에 빈 문자열로 놔두면 됩니다.

  • Notification notification = builder.build();
    Builder 객체를 생성해주었으니, Builder 객체를 이용하여 Notification 의 객체를 생성해줍시다.

  • notificationManager.notify(100,notification);
    Notification 매니저에게 알림을 보이도록 요청해야 합니다. 두번째 파라미터로 위에서 만든 Notification 의 객체를 전달해주면 됩니다.

이렇게 해서 Builder 객체의 생성과 Notification의 생성이 끝났습니다. 이제 Builder 객체를 이용하여 Notification 의 설정등을 알아봅시다.

Builder 를 이용한 알림창 꾸미기

void clickBtn(){

    if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.O){

        Uri uri = Uri.parse("android.resource://"+ getPackageName() + "/" +R.raw.s_sijak); 
        channel.setSound(uri,new AudioAttributes.Builder().build());
        channel.setVibrationPattern(new long[]{0,2000,1000});

        notificationManager.createNotificationChannel(channel);
        
        builder = new NotificationCompat.Builder(this,"ch01");
    }else {
        builder = new NotificationCompat.Builder(this,""); 
        Uri uri = Uri.parse("android.resource://"+ getPackageName() + "/" +R.raw.s_sijak);
        builder.setSound(uri);
    }

    builder.setSmallIcon(R.drawable.ic_noti);
    builder.setContentTitle("우산알림");
    builder.setContentText("우산 들고가세요~");
    Resources res = getResources();
    Bitmap bm = BitmapFactory.decodeResource(res,R.drawable.one_chopa); 
    builder.setLargeIcon(bm);

    Intent intent = new Intent(this, SecondActivity.class);
    PendingIntent pendingIntent = PendingIntent.getActivity(this,10,intent,PendingIntent.FLAG_IMMUTABLE); 
    builder.setContentIntent(pendingIntent);
    builder.setAutoCancel(true);

    NotificationCompat.BigPictureStyle style = new NotificationCompat.BigPictureStyle();
    style.bigPicture(BitmapFactory.decodeResource(getResources(),R.drawable.bg_one09));
    builder.setStyle(style);
    builder.addAction(R.drawable.bg_one09, "setting",pendingIntent);

    Notification notification = builder.build();
    notificationManager.notify(100,notification);
}

알림 사운드와 진동 등의 설정은 채널이 있을 때와 없을 때를 구분지어 코드를 작성해주어야 합니다. 일단 사운드 설정부터 알아봅시다.

  • Uri uri = Uri.parse("android.resource://"+ getPackageName() + "/" +R.raw.s_sijak);
    채널에 setSound() 를 하기 위해서는 uri 객체가 필요합니다. 그리고 Uri 의 객체를 만들기 위해 Resource 에 넣어둔 mp3 파일과 패키지 명이 필요합니다. 또한 android.resource: 은 정해진 이름이므로 틀리지 않게 적어줍시다. 또한 패키지명과 mp3 파일은 / 을 이용하여 구분해줍시다.

  • channel.setSound(uri,new AudioAttributes.Builder().build());
    Uri 객체를 만들었다면, 채널 객체에게 사운드 설정을 요청해야 합니다. Uri 객체와 AudioAttributes 객체를 전달해주어야 사운드 설정이 가능합니다.

  • channel.setVibrationPattern(new long[]{0,2000,1000});
    진동 설정도 가능합니다. long 배열 객체를 파라미터로 전달해주어 진동의 패턴을 설정할 수 있습니다. 또한 API 26 이전 버전 또한 개념은 동일 합니다. 다만 채널에게 사운드 설정을 요구하는 것이 아닌 Builder 객체에게 요청합니다.

  • builder.setSmallIcon(R.drawable.ic_noti);
    알림창 왼쪽의 작은 이미지를 설정할 수 있습니다.

  • builder.setContentTitle("우산알림");
    알림창의 제목을 설정할 수 있습니다.

  • builder.setContentText("우산 들고가세요~");
    알림창의 내용을 설정할 수 있습니다.

  • builder.setLargeIcon(bm);
    알림창에 오른쪽에 큰 이미지를 설정할 수 있습니다. 그러기 위해 먼저 Resources res = getResources(); 으로 Resource 의 객체하나를 가져오고, Bitmap bm = BitmapFactory.decodeResource(res,R.drawable.one_chopa); 으로 비트맵 파일을 하나 만들어줍니다. 그리고 만들어진 비트맵 파일을 setLargeIcon() 의 파라미터로 전달해주면 됩니다.

  • Intent intent = new Intent(this, SecondActivity.class);
    이번에는 알림창을 누르면 다른 화면을 띄우는 작업을 해봅시다. 일단 다른 액티비티로 넘어간다는 이야기는 인텐트가 필요하다는 의미이므로, 명시적 인텐트 하나를 만들어주었습니다. 우리가 넘어갈 화면은 SecondActivity 입니다.

  • PendingIntent pendingIntent = PendingIntent.getActivity(this,10,intent,PendingIntent.FLAG_IMMUTABLE);
    우리는 버튼을 눌렀을 때 바로 startActivity 가 되면 안되고, 알림창을 눌렀을 때 화면이 바뀌어야 합니다. 즉, 보류중인 인텐트(PendingIntent) 가 필요합니다. 첫번째 파라미터로는 Context 객체가, 두번째는 알림 식별코드를, 세번째 파라미터로는 전달할 인텐트를, 네번째 파라미터로는 flag 를 전달해주어야 합니다. flag 는 알림이 여러개 중복으로 떴을 때 어떻게 처리할지를 묻는 파라미터인데, FLAG_IMMUTABLE 을 사용한다고 생각합시다.

  • builder.setContentIntent(pendingIntent);
    만들어진 PendingIntent 객체를 파라미터로 전달하면 알림창을 클릭했을 때 화면을 전환할 수 있습니다.

  • builder.setAutoCancel(true);
    알림창을 클릭하여 화면을 전환하면 상태표시줄의 작은 아이콘 이미지를 자동으로 없애줍니다. 단, 이 기능은 인텐트를 활용할 때만 사용이 가능합니다.

  • NotificationCompat.BigPictureStyle style = new NotificationCompat.BigPictureStyle();
    요즘 자주 보이는 알림창 스타일 꾸미기 입니다. 알림창 중앙에 아주 큰 이미지를 넣을 수 있습니다.
    style.bigPicture(BitmapFactory.decodeResource(getResources(),R.drawable.bg_one09)); 을 이용하여 큰 이미지를 설정합시다. 그리고 builder.setStyle(style); 으로 빌더에게 스타일 적용을 요청합시다.

  • builder.addAction(R.drawable.bg_one09, "setting",pendingIntent);
    알림창을 클릭하는 액션을 추가할 수 있습니다. 원래는 기존과는 다른 pendingIntent 를 통해 SecondActivity 가 아닌 다른 액티비티로 넘어가야 합니다.


BroadcastReceiver

디바이스의 특정 상태 [문자수신, 배터리부족, 부팅완료, gps 상태정보 등등..] 를 운영체제에서 방송을 해주면 이를 수신할 때 사용하는 리시버 입니다.

전화가 오거나, 배터리가 부족하거나의 특정 상태가 발생하면, 앱이 켜져있든 꺼져있든 상관없이 모든 앱들에게 이 상태를 공유해줍니다. 이러한 공유방식이 Broadcast 방식입니다. 그래서 모든 앱은 이러한 정보를 받아볼 수 있습니다. 그리고 이러한 정보를 유의미한 상태로 이용하기 위해서는 이를 수신하는 수신기가 필요합니다. 그 수신기가 BroadcastReceiver 입니다.

또한 방송을 OS 에서뿐 아니라 우리가 만든 앱에서도 보낼 수 있습니다. 이번 테스트를 통해 Broadcast 를 보내보고 받아와 보겠습니다.


Broadcast 보내기

원래는 안드로이드라는 OS 가 보내는 정보 입니다. 이번 테스트는 실습 목적이기 때문에 보내보는것입니다. 일단, Broadcast 를 전송한다는것은 Intent 객체를 모든 앱에게 전달하는 모습입니다. 그리고 Broadcast 를 전달하는 과정에서 명시적 인텐트를 사용할 수도 있고, 암시적 인텐트를 사용할 수도 있습니다.

테스트를 위해 BroadcastReceiver 를 상속받는 MyReceiver 를 일단 만들어둡시다.

public class MyReceiver extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {
        Toast.makeText(context, "received", Toast.LENGTH_SHORT).show();
    }
}

BroadcastReceiver 를 상속받으면 반드시 구현해야하는 메소드가 onReceive() 입니다. 브로드캐스트를 수신했을 때 자동으로 실행되는 콜백메소드 이며, 파라미터로 따라오는 Intent 객체는 브로드캐스트가 발신할 때 보내는 인텐트 입니다. 또한 브로드캐스트는 운영체제의 능력이 없기 때문에 파라미터로 Context 객체를 전달받습니다.

추가적으로 브로드캐스트 또한 안드로이드의 4대 컴포넌트 이므로 메니페스트 파일에 등록해줍시다.

<receiver android:name=".MyReceiver"
    android:exported="true">

</receiver>

이번 테스트에서는 브로드캐스트의 수신결과를 확인하기 위해 토스트를 하나 띄웠습니다.

명시적, 암시적 인텐트

이제 브로드캐스트의 발신에서 사용되는 명시적 인텐트와 암시적 인텐트를 알아봅시다.

  • 명시적 인텐트 : 특정 리시버에게만 보내는 Broadcast
Intent intent = new Intent(this, MyReceiver.class);
sendBroadcast(intent);

Activity 전환시 사용했던 명시적 인텐트와 사용법이 같습니다. 특정한 리시버에게 브로드캐스트를 발신하고 싶을 때 사용합니다.

  • 암시적 인텐트 : Oreo 버전 부터 암시적 인텐트를 사용한 브로드캐스트 발신은 System 만 할 수 있도록 제한되었습니다. 만일, 리시버를 메니페스트가 아닌 자바에서 동적으로 등록한다면 암시적 인텐트를 보내는 테스트 정도는 가능합니다.
<receiver android:name=".MyReceiver"
    android:exported="true">
    <intent-filter>
        <action android:name="aaa"/>
    </intent-filter>
</receiver>

메니페스트 파일에서 리시버를 등록하고 인텐트 필터안에 <action> 을 지정해주었습니다. 만일, OS 가 aaa 라는 이름의 브로드 캐스트를 발신한다면 이 리시버에서 받아볼 수 있습니다.

Intent intent = new Intent();
intent.setAction("aaa"); 
sendBroadcast(intent);

이와 마찬가지로 자바 코드에서 인텐트 하나를 생성하고, setAction("aaa"); 으로 액션을 지정해준 뒤 sendBroadcast(intent) 를 하여 브로드캐스트를 발신할 수 있습니다.

@Override
protected void onResume() {
    super.onResume();
    myReceiver = new MyReceiver();
    IntentFilter filter = new IntentFilter();
    filter.addAction("aaa");

    registerReceiver(myReceiver,filter);
}

리시버 객체를 하나 생성하고 인텐트 필터의 객체도 생성해줍니다. 이 객체를 이용하여 addAction() 메서드의 파라미터로 "aaa" 를 전달합시다. 그리고 registerReceiver(myReceiver,filter); 으로 리시버를 등록하면, 암시적 인텐트를 통해 브로드캐스트를 발신하고 수신해올 수 있습니다.

@Override
protected void onPause() {
    super.onPause();
    unregisterReceiver(myReceiver);
}

또한 이 리시버의 등록을 해제하기 위해서는 unregisterReceiver() 을 이용하면 해제가 가능합니다.


부팅 시 Broadcast 수신하기

BroadcastReceiver 초기 세팅하기

안드로이드 13 버전부터 Activity 가 없으면 토스트의 발동을 제한하기 시작했습니다. 그래서 이번 테스트에서는 로그값을 활용하여 테스트의 결과를 확인해봅시다.

이번에 해볼 테스트는 기기를 부팅했을 때, 브로드캐스트를 수신해보려 합니다. 그러면 먼저, BroadcastReceiver 를 상속받은 MyBootingReceiver 클래스를 하나 설계하고, onReceive() 메소드를 구현해놓읍시다.

public class MyBootingReceiver extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {

        Log.i("Ex60", "booting receive");
    }
}

그리고 BroadcastReceiver 는 안드로이드의 4대 컴포넌트 중 하나이므로, 메니페스트 파일에 등록부터 합시다.

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

부팅시 브로드캐스트를 수신하기 위해서는 퍼미션이 필요합니다. 위 코드를 작성해주어 퍼미션을 줍시다.

<receiver android:name=".MyBootingReceiver"
    android:exported="true"
    android:permission="android.permission.RECEIVE_BOOT_COMPLETED">
    <intent-filter>
        <action android:name="android.intent.action.BOOT_COMPLETED"/>
    </intent-filter>
</receiver>

위 쪽 퍼미션 외에도 android:permission="android.permission.RECEIVE_BOOT_COMPLETED" 을 이용하여 퍼미션을 추가로 등록해주어야 합니다. 위쪽 퍼미션은 앱에게 주는 퍼미션, 아래쪽 퍼미션은 리시버 자체의 퍼미션 입니다.

인텐트 필터를 이용하여 어떠한 브로드캐스트를 수신할것인지를 지정해줍시다. 우리는 부팅 시 발신되는 브로드캐스트를 수신해야 하므로, <action android:name="android.intent.action.BOOT_COMPLETED"/> 을 이용하여 인텐트 필터의 액션값을 지정합시다.

부팅시 발송되는 Broadcast 수신하기

안드로이드 N 버전 (API 25) 부터 부팅완료 브로드캐스트를 수신하려면, 앱을 설치한 이후에 적어도 1회 사용자가 직접 런처화면의 앱 아이콘을 클릭하여 실행한 이력이 있는 앱만 부팅완료 브로드캐스트가 수신이 가능합니다. 또한 안드로이드 10 버전 (API 29) 부터 리시버에서 직접 Activity를 실행하는것이 금지되었습니다. 그 대신 Notification 을 이용하여 사용자에게 신호를 주고 액티비티의 실행여부를 선택할 수 있게끔 하였습니다. 그 점을 인지하고, 이제 리시버 클래스의 onReceiver() 메소드를 구현합시다.

@Override
public void onReceive(Context context, Intent intent) {

    Log.i("Ex60", "booting receive");

    String action = intent.getAction();
    if (action.equals(Intent.ACTION_BOOT_COMPLETED)) {

        if (Build.VERSION.SDK_INT >= 29) {

            NotificationManagerCompat manager = NotificationManagerCompat.from(context);
            NotificationChannelCompat channelCompat = new NotificationChannelCompat.Builder("ch01", NotificationManager.IMPORTANCE_HIGH).setName("Ex60").build();
            manager.createNotificationChannel(channelCompat);
            NotificationCompat.Builder builder = new NotificationCompat.Builder(context, "ch01");

            builder.setSmallIcon(R.mipmap.ic_launcher_round);
            builder.setContentTitle("부팅완료");
            builder.setContentText("부팅이 완료되었습니다");

            if (ActivityCompat.checkSelfPermission(context, android.Manifest.permission.POST_NOTIFICATIONS) != PackageManager.PERMISSION_GRANTED) {

                return;
            }
            manager.notify(100, builder.build());
        }else {
            Intent i = new Intent(context, MainActivity.class);
            i.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
            context.startActivity(i);
        }
    }
}
  • String action = intent.getAction();
    리시버가 받아온 인텐트의 액션값을 가져와 문자열 변수 action 에 넣어주었습니다. 우리는 부팅완료에 관한 브로드캐스트를 수신해야 하므로, 이 액션값이 부팅 완료에 관련한 액션값인지를 먼저 판단해주어야 합니다.

  • action.equals(Intent.ACTION_BOOT_COMPLETED)
    if 문의 조건으로, 액션값과 브로드캐스트의 종류가 부팅완료인지를 판단합니다. 부팅완료라면 if 문의 실행문을 실행합니다.

  • Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q
    사용자 기기의 안드로이드 버전이 API 29 버전 이상인지 판단합니다. 맞다면, Notification 을 이용하여 사용자에게 신호를 줘서 액티비티의 실행여부를 선택하도록 해야합니다.

  • NotificationManagerCompat manager = NotificationManagerCompat.from(context);
    Notification 의 매니저 객체를 하나 만듭니다.

  • NotificationChannelCompat channelCompat = new NotificationChannelCompat.Builder("ch01", NotificationManager.IMPORTANCE_HIGH).setName("Ex60").build();
    if 문 안쪽 실행문을 실행하기 위해서는 API 29 버전 이상이어야 하므로, Oreo 버전 이상입니다. 그렇기 때문에 Notification 의 Channel 을 만들어줘야 합니다.

  • manager.createNotificationChannel(channelCompat);
    그리고 매니저에게 채널객체를 전달합시다.

  • NotificationCompat.Builder builder = new NotificationCompat.Builder(context, "ch01");
    Notification 을 생성해줄 수 있는 Builder 객체를 만듭니다. 생성자 파라미터로 Context 객체 하나와 채널의 id 값을 전달합시다.

  • builder.setSmallIcon(R.mipmap.ic_launcher_round);builder.setContentTitle("부팅완료"); 그리고 builder.setContentText("부팅이 완료되었습니다"); 을 이용해 Notification 의 설정을 해줍시다.

  • ActivityCompat.checkSelfPermission(context, android.Manifest.permission.POST_NOTIFICATIONS) != PackageManager.PERMISSION_GRANTED
    퍼미션이 허용되지 않았다면, 대행사 객체를 이용하여 퍼미션을 허용해주면 됩니다.

  • manager.notify(100, builder.build());
    매니저 객체에게 notify() 해줍시다.

만일 API 버전이 29 이하라면, 인텐트 객체하나를 만들어 준뒤, Context 객체를 이용하여 startActivity() 를 해주면됩니다. 다만, 이 앱에서 액티비티가 처음 실행되는거라면, 백스택이 생성되지 못했기 때문에 실행이 안될수 있어 i.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 코드를 넣어주어야 합니다.

profile
Developer

0개의 댓글