首页 > 解决方案 > 3个不同时间的警报管理器,第二个在第一个触发时触发而不是在指定时间触发(ANDROID STUDIO)

问题描述

所以我正在制作 BirthDate Reminder 应用程序,对于我制作的每个 BirthDate,我设置 3 个警报管理器在特定时间触发(我选择我的分钟和小时进行测试),所以我让 weekAlarm 让我们说在 8:00 和我的 dayBeforeAlarm 在 8 :01 和我的 onDateAlarm 在 8:02,所以 weekAlarm 应该在 8 点触发,dayBeforeAlarm 应该在 8:01 触发等等......,所以当我制作一个 Birthdate 时它很好并且它工作得很好但是当我制作多个时BirthDate 每当第一个 AlarmManager(weekAlarm) 被触发时,AlarmManagers 就会触发,所以如果我有 2 个 BirthDates 然后一次 weekAlarm 触发,立即触发 dayBeforeAlarm,如果我有 3 个 Birthdates 然后一次 weekAlarm 触发,立即触发 dayBeforeAlarm 和 onDateAlarm。请注意,我制作的所有生日都必须是同一日期. 我怎样才能让它在他们选择的时间开火?

生日制造者班

package com.gavle.birthdatereminder;

import androidx.appcompat.app.AppCompatActivity;

import android.app.AlarmManager;
import android.app.DatePickerDialog;
import android.app.PendingIntent;
import android.content.Context;
import android.content.Intent;
import android.graphics.Color;
import android.graphics.drawable.ColorDrawable;
import android.os.Bundle;
import android.text.Editable;
import android.text.TextWatcher;
import android.view.View;
import android.widget.Button;
import android.widget.DatePicker;
import android.widget.EditText;
import android.widget.TextView;

import java.util.ArrayList;
import java.util.Calendar;

public class BirthdateMaker extends AppCompatActivity {
    EditText name;
    EditText lastName;
    TextView date;
    String dateSaved;
    private DatePickerDialog datePicker;
    private DatePickerDialog.OnDateSetListener datePickerOnListener;
    Button save;
    ArrayList<String> nameList;
    ArrayList<String> lastNameList;
    ArrayList<String> dateList;
    Context context;
    int savedYear;
    int savedMonth;
    int savedDay;
    Boolean editing = false;
    int position = -1;
    int idNumber = 0;
    static int weekBeforeID = -1;
    static int dayBeforeID = 0;
    static int onDateID = 1;
    static int notifID = 0;
    static ArrayList<Integer> sameDate;


    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_birthdate_maker);
        context = this;
        Intent intent = getIntent();
        editing = intent.getBooleanExtra("saving", false);
        position = intent.getIntExtra("position", -1);
        name = findViewById(R.id.name);
        lastName = findViewById(R.id.lastName);
        date = findViewById(R.id.date);
        save = findViewById(R.id.save);
        System.out.println("weekBeforeID " + weekBeforeID);
        if (position != -1) {
            name.setText(MainActivity.nameList.get(position));
            if (MainActivity.lastNameList.get(position) != " ") {
                lastName.setText(MainActivity.lastNameList.get(position));
            }
            date.setText(MainActivity.dateList.get(position));
        }

        if (!name.getText().toString().isEmpty() && !date.getText().toString().isEmpty()) {
            save.setEnabled(true);
        }
        date.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Calendar calendar = Calendar.getInstance();
                int year = calendar.get(Calendar.YEAR);
                int months = calendar.get(Calendar.MONTH);
                int day = calendar.get(Calendar.DAY_OF_MONTH);
                System.out.println("date click listener runs  :D ");
                datePicker = new DatePickerDialog(BirthdateMaker.this, android.R.style.Theme_Holo_Dialog_NoActionBar_MinWidth, datePickerOnListener, year, months, day);
                datePicker.show();
                datePicker.getDatePicker().setMaxDate(System.currentTimeMillis());
                datePicker.getWindow().setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));


            }
        });
        datePickerOnListener = new DatePickerDialog.OnDateSetListener() {
            @Override
            public void onDateSet(DatePicker view, int year, int month, int dayOfMonth) {
                month = month + 1;
                String formattedDate = month + "/" + dayOfMonth + "/" + year;
                System.out.println("date runs :D");
                savedYear = year;
                savedMonth = month;
                savedDay = dayOfMonth;
                date.setText(formattedDate);

            }
        };


        TextWatcher textWatcher = new TextWatcher() {
            @Override
            public void beforeTextChanged(CharSequence s, int start, int count, int after) {

            }

            @Override
            public void onTextChanged(CharSequence s, int start, int before, int count) {
                String nameInput = name.getText().toString().trim();
                String lastNameInput = lastName.getText().toString().trim();
                String dateInput = date.getText().toString();

                save.setEnabled(!nameInput.isEmpty() && !dateInput.equals("Date Of Birth"));

                if (save.isEnabled()) {
                    dateSaved = dateInput;
                }

            }

            @Override
            public void afterTextChanged(Editable s) {

            }
        };
        name.addTextChangedListener(textWatcher);
        lastName.addTextChangedListener(textWatcher);
        date.addTextChangedListener(textWatcher);

        save.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                if (editing == false) {
                    nameList = new ArrayList<>();
                    lastNameList = new ArrayList<>();
                    dateList = new ArrayList<>();
                    String savedName = name.getText().toString();
                    String savedLastName = lastName.getText().toString();
                    if (savedLastName.isEmpty()) {
                        savedLastName = " ";
                    }
                    setNotifications(savedYear,savedMonth,savedDay,dateSaved);
                    MainActivity.nameList.add(savedName);
                    MainActivity.lastNameList.add(savedLastName);
                    MainActivity.dateList.add(dateSaved);
                    MainActivity.setAdapter();
                    datePicker.dismiss();
                } else {
                    String savedName = name.getText().toString();
                    String savedLastName = lastName.getText().toString();
                    String savedDate = date.getText().toString();
                    if (savedLastName.isEmpty()) {
                        savedLastName = " ";
                    }
                    MainActivity.nameList.set(position, savedName);
                    MainActivity.lastNameList.set(position, savedLastName);
                    MainActivity.dateList.set(position, savedDate);
                    MainActivity.setAdapter();

                }




                System.out.println("name List " + nameList);
                finish();

            }
        });

    }
    public void setNotifications(int year, int month, int day,String dateSaved){
        if(year != -1 && month != -1 && day != -1){
            month = month - 1;
            if(MainActivity.nameList.isEmpty()){
                System.out.println("empty name list runs ");
                setWeekBefore(year,month,day,false);
                setDayBefore(year,month,day,false);
                setOnDate(year,month,day,false);

            }
            else{
                boolean isThereSameDate = checkSameDate(dateSaved);
                System.out.println("is there same date = " + isThereSameDate);
                if(!isThereSameDate){
                    System.out.println("if part runs false");
                    setWeekBefore(year,month,day,false);
                    setDayBefore(year,month,day,false);
                    setOnDate(year,month,day,false);

                }
                else{
                    System.out.println("else part runs true");
                    setWeekBefore(year,month,day,true);
                    setDayBefore(year,month,day,true);
                    setOnDate(year,month,day,true);

                }

            }

        }
    }

    public void setWeekBefore(int year, int month, int day, boolean isSameDate){
        System.out.println("week alarm went off");
        Calendar calendar = Calendar.getInstance();
        calendar.set(Calendar.YEAR,year);
        calendar.set(Calendar.MONTH,month);
        calendar.set(Calendar.DAY_OF_MONTH,day);
        calendar.set(Calendar.AM_PM,Calendar.PM);
        calendar.set(Calendar.HOUR,9);
        calendar.set(Calendar.MINUTE,46);
        calendar.set(Calendar.SECOND,0);
        System.out.println("is same date in methods " + isSameDate);
        Intent weekIntent = new Intent(this, NotificationMaker.class);

        System.out.println("week before ID " + weekBeforeID);
        weekIntent.putExtra("isSameDate",isSameDate);
        PendingIntent weekPendingIntent = PendingIntent.getBroadcast(this,setWeekBeforeID(),weekIntent,0);
        AlarmManager weekAlarm = (AlarmManager) getSystemService(context.ALARM_SERVICE);
        weekAlarm.setExact(AlarmManager.RTC_WAKEUP,calendar.getTimeInMillis(),weekPendingIntent);

    }

   public void setDayBefore(int year, int month, int day,  boolean isSameDate){
        Calendar calendar = Calendar.getInstance();
        calendar.set(Calendar.YEAR,year);
        calendar.set(Calendar.MONTH,month);
        calendar.set(Calendar.DAY_OF_MONTH,day);
        calendar.set(Calendar.AM_PM,Calendar.PM);
        calendar.set(Calendar.HOUR,9);
        calendar.set(Calendar.MINUTE,47);
        calendar.set(Calendar.SECOND,0);

        System.out.println("is same date in methods " + isSameDate);
       System.out.println("day before ID " + dayBeforeID);
        Intent dayBeforeIntent = new Intent(context,NotificationMaker.class);
        dayBeforeIntent.putExtra("isSameDate",isSameDate);
        PendingIntent dayBeforePendingIntent = PendingIntent.getBroadcast(context,setDayBeforeID(),dayBeforeIntent,0);
        AlarmManager dayBeforeAlarm = (AlarmManager) getSystemService(context.ALARM_SERVICE);
        dayBeforeAlarm.setExact(AlarmManager.RTC_WAKEUP,calendar.getTimeInMillis(),dayBeforePendingIntent);
       System.out.println("calendar in day before " + calendar.getTimeInMillis() + " and " + calendar.getTime());

    }

    public void setOnDate(int year, int month, int day,  boolean isSameDate){
        Calendar calendar = Calendar.getInstance();
        calendar.set(Calendar.YEAR,year);
        calendar.set(Calendar.MONTH,month);
        calendar.set(Calendar.DAY_OF_MONTH,day);
        calendar.set(Calendar.AM_PM,Calendar.PM);
        calendar.set(Calendar.HOUR,9);
        calendar.set(Calendar.MINUTE,48);
        calendar.set(Calendar.SECOND,0);
        System.out.println("is same date in methods " + isSameDate);
        System.out.println("on date ID " + onDateID);
        Intent onDateIntent = new Intent(context,NotificationMaker.class);
        onDateIntent.putExtra("isSameDate",isSameDate);
        PendingIntent onDatePendingIntent = PendingIntent.getBroadcast(context,setOnDateID(),onDateIntent,0);
        AlarmManager onDateAlarm = (AlarmManager) getSystemService(context.ALARM_SERVICE);
        onDateAlarm.setExact(AlarmManager.RTC_WAKEUP,calendar.getTimeInMillis(),onDatePendingIntent);
    }

    public int setWeekBeforeID(){
        weekBeforeID = weekBeforeID + 1;
        return weekBeforeID;
    }

    public int setDayBeforeID(){
        dayBeforeID = dayBeforeID + 1;
        return dayBeforeID;
    }
    public int setOnDateID(){
        onDateID = onDateID + 1;
        return onDateID;
    }

    @Override
    public void onBackPressed() {
        super.onBackPressed();

    }

    public boolean checkSameDate(String dateSaved) {
        ArrayList<String> dateList = MainActivity.dateList;
        sameDate = new ArrayList<>();
        for (int i = 0; i < dateList.size(); i++) {
            if (dateSaved.equals(dateList.get(i))) {
                sameDate.add(i);
            }
        }

       /* for(int z = 0; z < sameDate.size(); z++){
            for(int g = z + 1; g < sameDate.size(); g++){
                if(sameDate.get(z).equals(sameDate.get(g))){
                    sameDate.remove(g);
                }
            }
        }*/
        System.out.println(sameDate + "same date");
        if (!sameDate.isEmpty()) {
            return true;
        } else {

            return false;
        }
    }


}

onRecieve 类


package com.gavle.birthdatereminder;

import android.app.Notification;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;

import androidx.core.app.NotificationCompat;
import androidx.core.app.NotificationManagerCompat;

import static com.gavle.birthdatereminder.NotificationChannels.channelID;

public class NotificationMaker extends BroadcastReceiver {
    static int number = -1;
    static boolean isSameDate;
    @Override
    public void onReceive(Context context, Intent intent) {
        int ID = numberID();
        System.out.println("ID count " + ID);
        isSameDate = intent.getBooleanExtra("isSameDate",false);
        System.out.println("IsSameDate" + isSameDate);
        Notification notification = new NotificationCompat.Builder(context,channelID)
                .setSmallIcon(R.drawable.ic_baseline_add_24)
                .setContentTitle("title")
                .setContentText(String.valueOf(ID))
                .build();
        MainActivity.notificationManager.notify(ID,notification);
//        System.out.println("in on receieve" + BirthdateMaker.sameDate.get(BirthdateMaker.sameDate.size() - 1));
    }

    public int numberID() {
        if (isSameDate == true) {
            int ID = BirthdateMaker.sameDate.get(BirthdateMaker.sameDate.size() - 1);
            System.out.println("ID ID  gets called");
            return ID;
        } else {
            number = number + 1;
            int ID = number;
            System.out.println("number number gets called");
            return ID;
        }
    }
}

标签: androidandroid-intentalarmmanagerandroid-pendingintent

解决方案


您需要使每个都PendingIntent独一无二,否则您只需用新的覆盖旧的。您可以PendingIntent通过使用唯一的 ACTION、requestCode 或 DATA 来使自己独一无二。在您的情况下,我会将 ACTION 设置Intent为唯一的字符串(即:“BEFORE-WEEK”、“BEFORE-DAY”、“ON-DAY”)并附加一个字符串表示的生日,或者如果可以一个生日多次出现,您可以改为附加人名,这样可以确保每个人PendingIntent都是唯一的。


推荐阅读