본문 바로가기
[개발] 이야기/[Flutter] 이야기

[flutter] Local Notification 설정 및 구현하기 android, ios 모두 가능하게, 등록한 알림 지우기 remove

by 헤이나우
반응형

목차

    Flutter Local Notification 패키지 설명

    - 플루터에서 현재 사용하고 있는 기기에 알림을 보내기 위해서 사용하는 패키지이다. pub.dev사이트의 flutter_local_notification을 찾아보면 좋아요가 5천 개를 넘는 걸 볼 수 있다. 5천 개 이상이면 대단히 높은 수치이나 그만큼 이 플로그인의 안정성이 확이 되었고 많은 사람들이 사용하고 있다는 증거일 것이다. 그럼 힘들게 구현하지 말고 이 플러그인을 사용해서 기기에 알림을 보내는 기능을 만들어 보자!

     

    1. flutter_local_notifications 설치 하기

    - https://pub.dev/packages/flutter_local_notifications 접속 후 설치 링크 복사

    - pubspec.yaml의 dependencies에 입력 후 pub.get 입력

    2. Android 설정

    - 알림을 수신하기 위해선 여러 가지 권한이 필요한데 안드로이드에서 알림을 수신할 수 있는 권한을 선언해야 한다.

    - 안드로이드 권한 설정 -> /android/app/src/main/AndroidManifest.xml

    <manifest xmlns:android="http://schemas.android.com/apk/res/android">
    
        <!--local notification 권한 설정-->
        <uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>
        <uses-permission android:name="android.permission.VIBRATE" />
        <uses-permission android:name="android.permission.WAKE_LOCK" />
        <uses-permission android:name="android.permission.USE_FULL_SCREEN_INTENT" />
        <!--local notification 권한 설정-->
        
        <application
            android:label="@string/app_name"
            android:name="${applicationName}"
            android:icon="@mipmap/ic_launcher">
            <activity
                android:name=".MainActivity"
                android:showWhenLocked="true"
                android:turnScreenOn="true"
                android:exported="true"
                android:launchMode="singleTop"
                android:theme="@style/LaunchTheme"
                android:configChanges="orientation|keyboardHidden|keyboard|screenSize|smallestScreenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode"
                android:hardwareAccelerated="true"
                android:windowSoftInputMode="adjustResize">
                <meta-data
                  android:name="io.flutter.embedding.android.NormalTheme"
                  android:resource="@style/NormalTheme"
                  />
    
                <intent-filter>
                    <action android:name="android.intent.action.MAIN"/>
                    <category android:name="android.intent.category.LAUNCHER"/>
                </intent-filter>
            </activity>
            
            <!--local notification 권한 설정-->
            <receiver android:name="com.dexterous.flutterlocalnotifications.ScheduledNotificationReceiver" android:exported="false" />
            <receiver android:name="com.dexterous.flutterlocalnotifications.ScheduledNotificationBootReceiver" android:exported="false">
                <intent-filter>
                    <action android:name="android.intent.action.BOOT_COMPLETED"/>
                    <action android:name="android.intent.action.MY_PACKAGE_REPLACED"/>
                    <action android:name="android.intent.action.QUICKBOOT_POWERON" />
                </intent-filter>
            </receiver>
            <!--local notification 권한 설정-->
            
        </application>
    </manifest>

    - <!--local notification 권한 설정 --> 주석사이의 코드만 확인하면 된다.

    2-1. uses-permission

    - 알림을 받기 위해서 설정하는 권한들이다.

    - 진동을 울린다거나, 핸드폰을 깨우는 기능을 준다거나 하는 권한들이 포함되어 있다 저 4가지는 꼭 입력해 주자.

    2-2. receiver

    - 현재 등록된 알림들이 핸드폰이 재부팅되었을 때도 유지되도록 리시브를 만들어 재부팅될 때 해당 리시브가 실행되게 해 준다. 

    - receiver의 android:name은 플로그인에서 제공되는 경로로 변경하지 말고 그대로 복사 붙여 넣기 해주자.

    2-3 잠금상태에서 알림 보이게 하기

    android:showWhenLocked="true"
    android:turnScreenOn="true"

    3. iOS설정

     - /ios/Runner/AppDelegate.swift

    import UIKit
    import Flutter
    
    @UIApplicationMain
    @objc class AppDelegate: FlutterAppDelegate {
      override func application(
        _ application: UIApplication,
        didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?
      ) -> Bool {
    //이 부분을 입력해 주자
        if #available(iOS 10.0, *) {
            UNUserNotificationCenter.current().delegate = self as? UNUserNotificationCenterDelegate
        }
    
    
        GeneratedPluginRegistrant.register(with: self)
        return super.application(application, didFinishLaunchingWithOptions: launchOptions)
      }
    }

    4. flutter에서 사용하기 & 코드 작성

    4-1. 초기화하기

    - main함수 상단에서 빌드되기 전에 Notification서비스를 사용하기 위해 초기화해야 합니다.

    - android와 달리 ios푸시 관련 권한을 사용자에게 받는 로직만 주의해 주자.

    void main() async {
      WidgetsFlutterBinding.ensureInitialized();
      
      await _initNotiSetting(); //local Notifcation 초기 설정
      
      .
      .
      .
      build..
    }
    
    Future<void> _initNotiSetting() async {
      //Notification 플로그인 객체 생성
      final flutterLocalNotificationsPlugin = FlutterLocalNotificationsPlugin();
    
      //안드로이드 초기 설정
      final AndroidInitializationSettings initSettingsAndroid =
          AndroidInitializationSettings('@mipmap/ic_launcher');
    
      // IOS 초기 설정(권한 요청도 할 수 있음) 
      // request...값을 true로 설정 시 앱이 켜지자마자 권한 요청을 함
      final DarwinInitializationSettings initSettingsIOS =
          DarwinInitializationSettings(
              requestSoundPermission: true,
              requestBadgePermission: true,
              requestAlertPermission: true);
    
      //Notification에 위에서 설정한 안드로이드, IOS 초기 설정 값 삽입
      final InitializationSettings initSettings = InitializationSettings(
        android: initSettingsAndroid,
        iOS: initSettingsIOS,
      );
      await flutterLocalNotificationsPlugin.initialize(
        initSettings,
      );
      //Notification 초기 설정
      //onSelectNotification 옵션을 넣어서 메세지를 누르면 작동되는 콜백 함수를 생성 할 수 있다.(안써도됨)
      //안쓰게되면 해당 노티 클릭시 앱을 그냥 실행한다.
      //await flutterLocalNotificationsPlugin.initialize(initSettings,onSelectNotification:[콜백] );
    }

    4-2. notification 클래스 만들기

    - 실제 Noti기능을 사용하는 코드이다. 자세한 내용은 주석과 함께 코드를 확인해 보자.

    static Future sendLocalNotificationDateTime({
        required int idx,
        required DateTime date,
        required String title,
        required String content,
      }) async {
        bool? result = null;
        final flutterLocalNotificationsPlugin = FlutterLocalNotificationsPlugin();
        
        if (Platform.isAndroid) {
          //Android 일경우 무조건 true
          result = true;
        } else {
          //IOS 일때 현재 권한(알림)을 체크하여 사용자에게 권한을 요청한다.
          result = await flutterLocalNotificationsPlugin
              .resolvePlatformSpecificImplementation<
                  IOSFlutterLocalNotificationsPlugin>()
              ?.requestPermissions(
                alert: true,
                badge: true,
                sound: true,
              );
        }
        //기종별 알림 설정을 해준다.
        var android = AndroidNotificationDetails(
          'id',
          title,
          channelDescription: content,
          importance: Importance.max,
          priority: Priority.max,
          color: const Color.fromARGB(255, 255, 0, 0),
        );
    
        var ios = DarwinNotificationDetails();
        //기종별 설정값
        var detail = NotificationDetails(android: android, iOS: ios);
        //result: 권한여부
        if (result == true) {
          await flutterLocalNotificationsPlugin
              .resolvePlatformSpecificImplementation<
                  AndroidFlutterLocalNotificationsPlugin>()
              ?.deleteNotificationChannelGroup('id');
          //실제 기기 스케줄러에 해당 알림을 등록한다.
          // _setNotiTime에서 알림을 보낼 시간을 설정할 수 있다.
          await flutterLocalNotificationsPlugin.zonedSchedule(
            idx, // 스케줄 ID(고유)
            title, //알람 제목
            content, //알람 내용
            _setNotiTime(date: date), //알람 시간
            detail,
            //androidAllowWhileIdle: true,
            uiLocalNotificationDateInterpretation:
                UILocalNotificationDateInterpretation.absoluteTime,
            //이 옵션은 중요함(옵션 값에따라 시간만 맞춰서 작동할지, 월,일,시간 모두 맞춰서 작동할지 옵션 설정
            //아래와 같이 time으로 설정되어있으면, setNotTime에서 날짜를 아무리 지정해줘도 시간만 동일하면 알림이 발생
            matchDateTimeComponents:
                DateTimeComponents.dateAndTime, //또는dayOfMonthAndTime
          );
        }
      }
    
      static tz.TZDateTime _setNotiTime({
        required DateTime date,
      }) {
        tz.initializeTimeZones(); //TimeZone Database 초기화
        tz.setLocalLocation(tz.getLocation('Asia/Seoul')); //TimeZone 설정(외국은 다르게!)
        final now = tz.TZDateTime.now(tz.local);
        var scheduledDate = tz.TZDateTime(tz.local, now.year, now.month, now.day,
            date.hour, date.minute, date.second); //알람 시간
        //var test = tz.TZDateTime.now(tz.local).add(const Duration (seconds: 5));
        print('-----------알람 시간 체크----${scheduledDate.toString()}');
        return scheduledDate;
      }

    4-3 사용하기

    // idx : 알림 고유번호 
    // date : 알림 시간
    // title : 알림 제목
    //content: 알림 내용
    LocalNotification.sendLocalNotificationDateTime(idx: idx, date: endDT, title: "{title}", content: "content");

     

      4-4 등록한 알림 등록 해제방법

      static clear({required int idx}) {
          final flutterLocalNotificationsPlugin = FlutterLocalNotificationsPlugin();
          flutterLocalNotificationsPlugin.cancel(idx);
        }

       

       

      잠시만! [Hey To Do]앱을 소개합니다. 

      Hey To Do앱은 할일앱을 관리하는 심플한 앱입니다.

      할일을 등록하면 등록한 [할일]을 [캘린더]와 [해시태그]로 분류하여 관리할 수 있습니다.

       

      iOS, Android모두 다운로드 가능합니다.

       

      현재 무료 다운로드 가능합니다 

      꼭 한번 써보세요!

       

      안드로이드 다운로드

      https://play.google.com/store/apps/details?id=kr.co.heynow.todocalendar&pli=1

       

      iOS 다운로드

      https://apps.apple.com/us/app/hey-to-do-calendar-hashtag/id6475393572

       

       

       

      iOS, Android모두 다운로드 가능합니다.

       

      안드로이드 다운로드

      https://play.google.com/store/apps/details?id=kr.co.heynow.todocalendar&pli=1

       

      iOS 다운로드

      https://apps.apple.com/us/app/hey-to-do-calendar-hashtag/id6475393572

      반응형

      댓글