java - 从 ram 中清除后警报停止

标签 java android service alarmmanager android-alarms

我正在制作一个闹钟,它要求用户做一项特定的工作,以便在响铃时关闭闹钟。它工作正常,但问题是如果用户在闹钟响起时从最近的 Activity 中关闭闹钟应用程序,闹钟将停止响铃。我希望即使用户在响铃时清除应用程序,它也不应停止响铃。它应该只在给定的任务完成后停止。我该如何实现?

编辑 #1:闹钟响起时调用的 Activity

    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        Log.v(LOG_TAG, "in AlarmAlert");
        unlockScreen();
        setContentView(R.layout.activity_alarm_alert);

        Bundle bundle = this.getIntent().getExtras();
        alarm = (Alarm) bundle.getSerializable("alarm");
        alarmDatabase = new AlarmDatabase(this);

        //Uri uri = alarm.getRingtonePath();
        question = (TextView)findViewById(R.id.question);
        answer = (TextView) findViewById(R.id.answer);

        oldColors =  answer.getTextColors();
        diff = alarm.getDifficulty().toString();
        questionString = GenerateMathsQuestion.generateQuestion(diff);
        question.setText(questionString);
        actualAnswer = EvaluateString.evaluate(questionString);
        AudioManager am = (AudioManager)getSystemService(Context.AUDIO_SERVICE);

        int result = am.requestAudioFocus(focusChangeListener,
               AudioManager.STREAM_MUSIC,
               AudioManager.AUDIOFOCUS_GAIN);

        if (result == AudioManager.AUDIOFOCUS_REQUEST_GRANTED) {
            mediaPlayer = new MediaPlayer();
            mediaPlayer.setVolume(1.0f, 1.0f);
            mediaPlayer.setLooping(true);
            mediaPlayer.setAudioStreamType(AudioManager.STREAM_ALARM);

            try {
                mediaPlayer.setDataSource(this,   Uri.parse(alarm.getRingtonePath()));
                mediaPlayer.prepare();
            } catch (IOException e) {
                e.printStackTrace();
            }

            mediaPlayer.start();
        }

        if(alarm.getIsVibrate()) {
            vibrator = (Vibrator) getSystemService(VIBRATOR_SERVICE);
            long[] pattern = {1000, 200, 200, 200};
            vibrator.vibrate(pattern, 0);
        }
    }

public void closeAlarm(){
        Log.v(LOG_TAG, "will now stop");
        mediaPlayer.stop();
        if(vibrator!=null)
            vibrator.cancel();
        Log.v(LOG_TAG, "will now release");
        mediaPlayer.release();
        Log.v(LOG_TAG, "id of ringing alarm: " + alarm.getAlarmId());
        alarm.setIsActive(false);
        alarmDatabase.updateData(alarm);
        cursor = alarmDatabase.sortQuery();
        while(cursor.moveToNext()){
            int id = cursor.getInt(cursor.getColumnIndex(AlarmDatabase.COLUMN_UID));
            currentAlarm = alarmDatabase.getAlarm(id);
            Log.v(LOG_TAG, "id of next alarm " + id);
            if(currentAlarm != null) {
                if (currentAlarm.getIsActive() == true) {
                    currentAlarm.scheduleAlarm(this, true);
                    break;
                }
            }
        }
        this.finish();
    }

最佳答案

你应该使用 Services .看看它,这就是你想要的。通常你可以让它运行一个操作,服务不会返回任何结果。但即使您从任务管理器或空闲 RAM 中终止应用程序,它也会无限期运行。

我建议这个 tutorial阅读有关服务的信息。

更新

按以下方式使用该服务实现您的 Activity ,以便它可以与布局对话并在需要时停止警报。

public class HelloService extends Service {
  private Looper mServiceLooper;
  private ServiceHandler mServiceHandler;

  // Handler that receives messages from the thread
  private final class ServiceHandler extends Handler {
      public ServiceHandler(Looper looper) {
          super(looper);
      }
      @Override
      public void handleMessage(Message msg) {
          // Normally we would do some work here, like download a file.
          // For our sample, we just sleep for 5 seconds.
          try {
              Thread.sleep(5000);
          } catch (InterruptedException e) {
              // Restore interrupt status.
              Thread.currentThread().interrupt();
          }
          // Stop the service using the startId, so that we don't stop
          // the service in the middle of handling another job
          stopSelf(msg.arg1);
      }
  }

  @Override
  public void onCreate() {
    // Start up the thread running the service.  Note that we create a
    // separate thread because the service normally runs in the process's
    // main thread, which we don't want to block.  We also make it
    // background priority so CPU-intensive work will not disrupt our UI.
    HandlerThread thread = new HandlerThread("ServiceStartArguments",
            Process.THREAD_PRIORITY_BACKGROUND);
    thread.start();

    // Get the HandlerThread's Looper and use it for our Handler
    mServiceLooper = thread.getLooper();
    mServiceHandler = new ServiceHandler(mServiceLooper);
  }

  @Override
  public int onStartCommand(Intent intent, int flags, int startId) {
      Toast.makeText(this, "service starting", Toast.LENGTH_SHORT).show();

      // For each start request, send a message to start a job and deliver the
      // start ID so we know which request we're stopping when we finish the job
      Message msg = mServiceHandler.obtainMessage();
      msg.arg1 = startId;
      mServiceHandler.sendMessage(msg);

      // If we get killed, after returning from here, restart
      return START_STICKY;
  }

  @Override
  public IBinder onBind(Intent intent) {
      // We don't provide binding, so return null
      return null;
  }

  @Override
  public void onDestroy() {
    Toast.makeText(this, "service done", Toast.LENGTH_SHORT).show();
  }
}

关于java - 从 ram 中清除后警报停止,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36957382/

相关文章:

java - Joda Time 的 Period.getMillis 返回不准确的数字

java.lang.NoClassDefFoundError : bsh/EvalError 错误

android - 如何使用 Espresso 在 UI 测试中模拟 textwatcher?

java - 错误: No resource found that matches the given name (at 'theme' with value '@style/Theme.Sherlock' )

bash - 为什么 ftam 服务将启动并从终端返回提示,而不是从 bash 脚本?

android - 如何通知 Activity 有关服务的进度

grails - Grails Bootstrap XmlSlurper服务无结果

java - 如何解决Spring上下文的循环依赖?

java - 有没有一种令人满意的方法在 Java 中打印复杂的 PDF 文件

java - 无法在 intellij 中运行 java 11 示例程序