android 有一个闹铃管理的东西叫:AlarmManager;这个用来管理闹铃的发起和停止,我们可以service,broadcastreceiver或Activity来接受AlarmManager发出的信息,AlarmManager类通过getSystemService(Activity.ALARM_SERVICE)方法来实例化;在这里注意下这几个方法:

// 取消已经注册的与参数匹配的闹铃    
    void cancel(PendingIntent operation)  
      
      //注册一个新的闹铃   
    void set( int  type,  long  triggerAtTime, PendingIntent operation)  
      
      //注册一个重复类型的闹铃   
    void setRepeating( int  type,  long  triggerAtTime,  long  interval, PendingIntent operation)  
      
        //设置时区   
    void setTimeZone(String timeZone)


再来介绍下闹铃的几种样式:


public static final int ELAPSED_REALTIME
        //当系统进入睡眠状态时,这种类型的闹铃不会唤醒系统。直到系统下次被唤醒才传递它,该闹铃所用的时间是相对时间,是从系统启动后开始计时的,包括睡眠时间,可以通过调用SystemClock.elapsedRealtime()获得。系统值是3。

        public static final int ELAPSED_REALTIME_WAKEUP
        //能唤醒系统,用法同ELAPSED_REALTIME,系统值是2  。

        public static final int RTC
        //当系统进入睡眠状态时,这种类型的闹铃不会唤醒系统。直到系统下次被唤醒才传递它,该闹铃所用的时间是绝对时间,所用时间是UTC时间,可以通过调用 System.currentTimeMillis()获得。系统值是1 (0x00000001) 。

        public static final int RTC_WAKEUP
        //能唤醒系统,用法同RTC类型,系统值为 0 。

        Public static final int POWER_OFF_WAKEUP
        //能唤醒系统,它是一种关机闹铃,就是说设备在关机状态下也可以唤醒系统,所以我们把它称之为关机闹铃。使用方法同RTC类型,系统值为4。



下面看下小DEMO:

入口:AlarmActivity

package com.glacier.demo;

import java.util.Calendar;

import android.app.Activity;
import android.app.AlarmManager;
import android.app.PendingIntent;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.DatePicker;
import android.widget.DatePicker.OnDateChangedListener;
import android.widget.TextView;
import android.widget.TimePicker;
import android.widget.TimePicker.OnTimeChangedListener;
/***
 * 闹铃管理(提示:设置过去的时间会一直提示:大家在把时间设置成闹铃的时间取消即可)
 * @author wangyubin
 *
 */
public class AlarmActivity extends Activity implements OnClickListener {

	private TextView mTitleTv, mDatePickerTv, mTimePickerTv;
	private DatePicker mDatePicker;
	private TimePicker mTimePicker;
	private Button mInstallBtn, mCancelBtn;
	private Calendar calendar;

	private int year, month, day, hour, minute;

	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_alarm);
		init();
	}

	private void init() {

		mTitleTv = (TextView) findViewById(R.id.tv_title);
		mDatePicker = (DatePicker) findViewById(R.id.datePicker);
		mTimePicker = (TimePicker) findViewById(R.id.timePicker);
		mDatePickerTv = (TextView) findViewById(R.id.tv_datepicker);
		mTimePickerTv = (TextView) findViewById(R.id.tv_timepicker);
		mInstallBtn = (Button) findViewById(R.id.btn_install);
		mCancelBtn = (Button) findViewById(R.id.btn_cancel);
		calendar = Calendar.getInstance();
		// 得到当前时间并设置到日历里面
		calendar.setTimeInMillis(System.currentTimeMillis());
		// 获取到当前的时间
		year = calendar.get(Calendar.YEAR);
		month = calendar.get(Calendar.MONTH);
		day = calendar.get(Calendar.DATE);
		hour = calendar.get(Calendar.HOUR_OF_DAY);
		minute = calendar.get(Calendar.MINUTE);
		// 设置date控件的初始化以及监听
		mDatePicker.init(year, month, day, new OnDateChangedListener() {

			public void onDateChanged(DatePicker view, int year,
					int monthOfYear, int dayOfMonth) {
				mDatePickerTv.setText("您选择的日期是:" + year + "年"
						+ (monthOfYear + 1) + "月" + dayOfMonth + "日");
				AlarmActivity.this.year = year;
				AlarmActivity.this.month = monthOfYear;
				AlarmActivity.this.day = dayOfMonth;
			}

		});
		// 设置24小时制
		mTimePicker.setIs24HourView(true);
		mTimePicker.setOnTimeChangedListener(new OnTimeChangedListener() {

			public void onTimeChanged(TimePicker view, int hourOfDay, int minute) {
				mTimePickerTv.setText("您选择的时间是:" + hourOfDay + "时" + minute
						+ "分");
				AlarmActivity.this.hour = hourOfDay;
				AlarmActivity.this.minute = minute;
			}
		});
		// 设置闹铃按钮监听
		mInstallBtn.setOnClickListener(this);
		mCancelBtn.setOnClickListener(this);
	}

	@Override
	public void onClick(View v) {
		// TODO Auto-generated method stub
		switch (v.getId()) {
		// 这里讲一个我们遇到的命名的问题:仔细看case后面都带一个大括号,这样里面的switch里面的局部变量就变成了单独的case里面的局部变量,防止命名冲突
		case R.id.btn_install: {
			// 设置闹铃的时间(年,月,日,时,分,秒)
			calendar.set(year, month, day, hour, minute, 0);
			Intent intent = new Intent(this, AlamrReceiver.class);
			// 设置intent的动作,识别当前设置的是哪一个闹铃,有利于管理闹铃的关闭
			intent.setAction(year + "年" + month + "月" + day + "日" + hour + "时"
					+ minute + "分");
			// 用广播管理闹铃
			PendingIntent pi = PendingIntent.getBroadcast(this, 0, intent, 0);
			// 获取闹铃管理
			AlarmManager am = (AlarmManager) getSystemService(Activity.ALARM_SERVICE);
			// 设置闹钟
			am.set(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), pi);
			// 设置闹钟重复时间
			am.setRepeating(AlarmManager.RTC_WAKEUP,
					calendar.getTimeInMillis(), 10 * 1000, pi);
			// 获取到的月份是0~11,所以要加1
			int newMonth = month + 1;
			mTitleTv.setText("您选择的闹铃为:" + year + "年" + newMonth + "月" + day
					+ "日" + hour + "时" + minute + "分");
			break;
		}
		case R.id.btn_cancel: {
			Intent intent = new Intent(this, AlamrReceiver.class);
			// 找出当前控件选择的闹铃时间,并关闭当前选择的闹铃
			intent.setAction(year + "年" + month + "月" + day + "日" + hour + "时"
					+ minute + "分");
			PendingIntent pi = PendingIntent.getBroadcast(this, 0, intent, 0);
			AlarmManager am = (AlarmManager) getSystemService(Activity.ALARM_SERVICE);
			am.cancel(pi);
			int newMonth = month + 1;
			mTitleTv.setText("您取消了" + year + "年" + newMonth + "月" + day + "日"
					+ hour + "时" + minute + "分" + "的闹铃!!!");
			break;
		}
		}
	}

}


下面看下广播的接收:

package com.glacier.demo;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.widget.Toast;
/**
 * 闹铃接受器
 * @author wangyubin
 *
 */
public class AlamrReceiver  extends BroadcastReceiver {  
  
    @Override  
    public void onReceive(Context context, Intent intent) {  
        // TODO Auto-generated method stub 
        Toast.makeText(context, "闹钟时间到:"+intent.getAction(), Toast.LENGTH_LONG).show();  
    }  
}



这个广播需要注册成:

<receiver
            android:name=".AlamrReceiver"
            android:process=":remote" >
        </receiver>

android:process=":remote" 要注意是为了这个广播能被AlarmManager调用

还有布局文件activity_alarm:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_gravity="center_horizontal"
    android:orientation="vertical" >

    <TextView
        android:id="@+id/tv_title"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:gravity="center"
        android:text="@string/btn_install" />

    <DatePicker
        android:id="@+id/datePicker"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="27dp" />

    <TextView
        android:id="@+id/tv_datepicker"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" />

    <TimePicker
        android:id="@+id/timePicker"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" />
    
    <TextView
        android:id="@+id/tv_timepicker"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" />

    <LinearLayout
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal" >

        <Button
            android:id="@+id/btn_install"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_marginTop="10dp"
            android:layout_weight="1"
            android:text="@string/btn_install" />

        <Button
            android:id="@+id/btn_cancel"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_marginTop="10dp"
            android:layout_weight="1"
            android:text="@string/btn_cancel" />
    </LinearLayout>

</LinearLayout>



还有两个String:

<string name="btn_install">设置闹铃</string>
 <string name="btn_cancel">取消闹铃</string>

看真机下效果:想抓弹出来的吐司没抓到

删除一个docker 删除一个闹钟_ide