J'essaie de coder un bloc de code qui doit se réveiller plusieurs fois par jour et notifier un serveur. J'essaie d'utiliser une intention d'alarme et un récepteur de diffusion, mais le récepteur se déclenche rapidement à l'infini et je n'arrive pas à l'arrêter.
Tout mon code se trouve dans un seul fichier. Le déroulement du processus est simple. Réveillez-vous au démarrage, vérifiez si nous devons communiquer, essayez de communiquer, sinon configurez l'une des deux conditions d'attente, activez l'alarme. Réveillez-vous en cas d'alarme, essayez de communiquer, réactivez l'alarme si nécessaire, sinon tuez-la.
Quand je construire et déployer ce apk sur mon appareil le flux de processus suivant se produit:
reboot
récepteur reçoit l' intention très bien démarrage
alarme se prévue
intention d'alarme se déclenche au bout de 80 secondes comme prévu
puis après les 80 secondes,
puis connectez-chat montre le récepteur de radiodiffusion étant déclenché très rapidement.
Plusieurs fois par seconde, comme s'il s'agissait d'un spam.
Je suis complètement déconcerté de savoir pourquoi il se comporte comme ça
private PendingIntent pendingIntent;
/**
* Receive a signal, in our case, the device has booted up
* @param context The Context in which the receiver is running.
* @param intent The Intent being received.
*/
@SuppressLint("UnsafeProtectedBroadcastReceiver")
@Override
public void onReceive(Context context, Intent intent) {
Log.d("autostart", "broadcast received");
if(intent.getAction()==null)return;
Intent alarmIntent = new Intent(context, autostart.class);
alarmIntent.setAction("device.activation.alarm");
pendingIntent = PendingIntent.getBroadcast(context, 0, alarmIntent, PendingIntent.FLAG_CANCEL_CURRENT);//cancel flag seems to be ignored
cancel(context);//cancel command seems to be ignored
if (intent.getAction().equals("android.intent.action.BOOT_COMPLETED")) {
// Set the alarm here.
Log.d("autostart","We have booted");
RegisterActivation registerActivation = new RegisterActivation(context);
if(registerActivation.AlreadyActivated())
return;//no need
if(registerActivation.ActivationPending()){
//perform regular activation
return;
}
if(registerActivation.canComplete()){
boolean success = registerActivation.sendActivation();//talk to server
if(success) {
registerActivation.markCompleted();
cancel(context);
}
else {
registerActivation.markFileWaiting();
startPending(context);
}
return;
}
if(registerActivation.shouldWait()){//if can complete fails, then shouldWait will immediately return true
Log.d("autostart", "waiting");
registerActivation.markFileSimWait();
startWait(context);
return;
}
}
if(intent.getAction().equals("device.activation.alarm")){
Log.d("autostart","alarm triggered");
cancel(context);
RegisterActivation registerActivation = new RegisterActivation(context);
if(registerActivation.AlreadyActivated()){//for now always false
cancel(context);
return;
}
if(registerActivation.ActivationPending()){//for now always false
//same as before
return;
}
if(registerActivation.canComplete()){//glitch happens here
if(registerActivation.sendActivation()){
registerActivation.markCompleted();
cancel(context);
}else{
registerActivation.markFileWaiting();
startPending(context);//this immediatly triggers the broadcast recieve
}
return;
}
if(registerActivation.shouldWait()){
registerActivation.markFileSimWait();
startWait(context);
}
}
}
public void startPending(Context context) {
AlarmManager manager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
int interval = 80000;//will later become 4 hours
manager.set(AlarmManager.RTC_WAKEUP,interval,pendingIntent);
Log.d("autostart", "alarm activated");
}
public void startWait(Context context) {//same function but different time interval
AlarmManager manager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
int interval = 90000;// will later become 12 hours
manager.set(AlarmManager.RTC_WAKEUP, interval, pendingIntent);
}
public void cancel(Context context) {
AlarmManager manager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
manager.cancel(pendingIntent);
}
merci à Mike M. https://stackoverflow.com/users/2850651/mike-m
Je marquerais votre commentaire comme réponse mais vous avez seulement commenté
Je suis parti de
manager.set(AlarmManager.RTC_WAKEUP,interval,pendingIntent);
à:
manager.setInexactRepeating(AlarmManager.RTC_WAKEUP, System.currentTimeMillis()+interval, interval, pendingIntent);
J'ai dû ajouter l'intervalle au paramètre intervalMillis.
Et comme testé, la fonction manager.set (...) ne répond vraiment pas trop bien à ce que je veux qu'elle fasse donc je dois juste déclencher une annulation au début.
Merci encore Mike :)
Cet article est collecté sur Internet, veuillez indiquer la source lors de la réimpression.
En cas d'infraction, veuillez [email protected] Supprimer.
laisse moi dire quelques mots