是否有可能使用AlarmManager在沒有應用程序使用服務的情況下運行鬧鐘。 AlarmManager必須使設備退出睡眠模式並在onReceive中執行我的代碼。事實上,我在這裏發佈的每個代碼示例都顯示了正在使用的服務。然而,Android文檔沒有提到需要提供服務。使用AlarmManager沒有服務
回答
這裏是一個工作示例,
activity_alarm_manager.xml文件的代碼
<linearlayout android:layout_height="match_parent"
android:layout_width="match_parent" android:orientation="vertical"
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools">
<button android:id="@+id/btStart" android:layout_height="wrap_content"
android:layout_width="match_parent" android:onclick="startRepeatingTimer"
android:padding="@dimen/padding_medium" android:text="@string/btStart"
tools:context=".WidgetAlarmManagerActivity"/>
<button android:id="@+id/btCancel" android:layout_height="wrap_content"
android:layout_width="match_parent" android:onclick="cancelRepeatingTimer"
android:padding="@dimen/padding_medium" android:text="@string/btCancel"
tools:context=".WidgetAlarmManagerActivity"/>
<button android:id="@+id/btOneTime" android:layout_height="wrap_content"
android:layout_width="match_parent" android:onclick="onetimeTimer"
android:padding="@dimen/padding_medium" android:text="@string/btOneTime"
tools:context=".WidgetAlarmManagerActivity"/>
</linearlayout>
廣播接收器的代碼,
public class AlarmManagerBroadcastReceiver extends BroadcastReceiver {
final public static String ONE_TIME = "onetime";
@Override
public void onReceive(Context context, Intent intent) {
PowerManager pm = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
PowerManager.WakeLock wl = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "YOUR TAG");
//Acquire the lock
wl.acquire();
//You can do the processing here.
Bundle extras = intent.getExtras();
StringBuilder msgStr = new StringBuilder();
if(extras != null && extras.getBoolean(ONE_TIME, Boolean.FALSE)){
//Make sure this intent has been sent by the one-time timer button.
msgStr.append("One time Timer : ");
}
Format formatter = new SimpleDateFormat("hh:mm:ss a");
msgStr.append(formatter.format(new Date()));
Toast.makeText(context, msgStr, Toast.LENGTH_LONG).show();
//Release the lock
wl.release();
}
public void SetAlarm(Context context)
{
AlarmManager am=(AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(context, AlarmManagerBroadcastReceiver.class);
intent.putExtra(ONE_TIME, Boolean.FALSE);
PendingIntent pi = PendingIntent.getBroadcast(context, 0, intent, 0);
//After after 5 seconds
am.setRepeating(AlarmManager.RTC_WAKEUP, System.currentTimeMillis(), 1000 * 5 , pi);
}
public void CancelAlarm(Context context)
{
Intent intent = new Intent(context, AlarmManagerBroadcastReceiver.class);
PendingIntent sender = PendingIntent.getBroadcast(context, 0, intent, 0);
AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
alarmManager.cancel(sender);
}
public void setOnetimeTimer(Context context){
AlarmManager am=(AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(context, AlarmManagerBroadcastReceiver.class);
intent.putExtra(ONE_TIME, Boolean.TRUE);
PendingIntent pi = PendingIntent.getBroadcast(context, 0, intent, 0);
am.set(AlarmManager.RTC_WAKEUP, System.currentTimeMillis(), pi);
}
}
AndroidManifest.xml中的代碼
<manifest android:versioncode="1" android:versionname="1.0"
package="com.rakesh.alarmmanagerexample"
xmlns:android="http://schemas.android.com/apk/res/android">
<uses-sdk android:minsdkversion="10" android:targetsdkversion="15"/>
<uses-permission android:name="android.permission.WAKE_LOCK"/>
<application android:icon="@drawable/ic_launcher"
android:label="@string/app_name" android:theme="@style/AppTheme">
<activity android:label="@string/title_activity_alarm_manager"
android:name="com.rakesh.alarmmanagerexample.AlarmManagerActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<receiver android:name="com.rakesh.alarmmanagerexample.AlarmManagerBroadcastReceiver">
</receiver>
</application>
</manifest>
AlarmManagerActivity.java文件的代碼
public class AlarmManagerActivity extends Activity {
private AlarmManagerBroadcastReceiver alarm;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_alarm_manager);
alarm = new AlarmManagerBroadcastReceiver();
}
@Override
protected void onStart() {
super.onStart();
}
public void startRepeatingTimer(View view) {
Context context = this.getApplicationContext();
if(alarm != null){
alarm.SetAlarm(context);
}else{
Toast.makeText(context, "Alarm is null", Toast.LENGTH_SHORT).show();
}
}
public void cancelRepeatingTimer(View view){
Context context = this.getApplicationContext();
if(alarm != null){
alarm.CancelAlarm(context);
}else{
Toast.makeText(context, "Alarm is null", Toast.LENGTH_SHORT).show();
}
}
public void onetimeTimer(View view){
Context context = this.getApplicationContext();
if(alarm != null){
alarm.setOnetimeTimer(context);
}else{
Toast.makeText(context, "Alarm is null", Toast.LENGTH_SHORT).show();
}
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.activity_widget_alarm_manager, menu);
return true;
}
}
引用鏈從Github
您可以:
給
AlarmManager
一個PendingIntent
與特定BroadCastReciever
的意圖過濾器。聲明此接收器的應用程序的清單連同意圖 篩選器。
接收者的
onRecieve()
將被AlarmManager
調用。
否涉及服務。
,我不認爲它很重要我通過傳遞這是一個Context
設置從Activity
週期性事件,它似乎並沒有問題哪個上下文被傳遞。
傳遞的context
僅在正從PendingIntent.getBroadcast
的PendingIntent
和看source of 4.2.2使用:
/**
* Retrieve a PendingIntent that will perform a broadcast, like calling
* {@link Context#sendBroadcast(Intent) Context.sendBroadcast()}.
*
* @param context The Context in which this PendingIntent should perform
* the broadcast.
* @param requestCode Private request code for the sender (currently
* not used).
* @param intent The Intent to be broadcast.
* @param flags May be {@link #FLAG_ONE_SHOT}, {@link #FLAG_NO_CREATE},
* {@link #FLAG_CANCEL_CURRENT}, {@link #FLAG_UPDATE_CURRENT},
* or any of the flags as supported by
* {@link Intent#fillIn Intent.fillIn()} to control which unspecified parts
* of the intent that can be supplied when the actual send happens.
*
* @return Returns an existing or new PendingIntent matching the given
* parameters. May return null only if {@link #FLAG_NO_CREATE} has been
* supplied.
*/
public static PendingIntent getBroadcast(Context context, int requestCode,
Intent intent, int flags) {
return getBroadcastAsUser(context, requestCode, intent, flags,
new UserHandle(UserHandle.myUserId()));
}
/**
* @hide
* Note that UserHandle.CURRENT will be interpreted at the time the
* broadcast is sent, not when the pending intent is created.
*/
public static PendingIntent getBroadcastAsUser(Context context, int requestCode,
Intent intent, int flags, UserHandle userHandle) {
String packageName = context.getPackageName();
String resolvedType = intent != null ? intent.resolveTypeIfNeeded(
context.getContentResolver()) : null;
try {
intent.setAllowFds(false);
IIntentSender target =
ActivityManagerNative.getDefault().getIntentSender(
ActivityManager.INTENT_SENDER_BROADCAST, packageName,
null, null, requestCode, new Intent[] { intent },
resolvedType != null ? new String[] { resolvedType } : null,
flags, null, userHandle.getIdentifier());
return target != null ? new PendingIntent(target) : null;
} catch (RemoteException e) {
}
return null;
}
你可以看到,通過context
僅用於獲取包名和解決的類型和不存儲在PendingIntent
或任何可能導致一些問題和泄漏的東西。
這似乎不是真的。我在Pending意圖中使用了一個動作,而不是使用上下文,然後onReceive被解僱了。使用上下文最初在我的應用程序中工作,但最終未能觸發。使用動作保證AlarmManager將創建你的類的一個實例。上下文並不完全相同,並且有很多人在接受解僱時遇到問題。 – AndroidDev 2013-04-20 12:20:35
@AndroidDev你是如何得到一個廣播'PendingIntent'而不通過'context'傳遞的?你沒有使用這個函數:http://developer.android.com/reference/android/app/PendingIntent.html#getBroadcast (android.content.Context,%20int,%20android.content.Intent,%20int) – 2013-04-20 12:30:55
I指的是Intent,而不是getBroadcast的上下文參數。您不需要意向的上下文。我使用動作信息。 – AndroidDev 2013-04-20 15:15:54
- 1. 沒有喚醒的Android AlarmManager服務
- 2. 使用AlarmManager撥打服務
- 3. AlarmManager或服務
- 4. 服務與AlarmManager
- 5. alarmmanager和服務
- 6. Android AlarmManager服務
- 7. 在服務中調用AlarmManager
- 8. Android AlarmManager使用鈴聲啓動服務
- 9. Android AlarmManager或服務?
- 10. 使用AlarmManager啓動服務,該服務可能已在運行
- 11. 具有AlarmManager建議的Android服務
- 12. AlarmManager和服務 - 啓動多個服務?
- 13. 我AlarmManager,廣播接收器和服務沒有啓動,
- 14. AlarmManager無法啓動服務
- 15. AlarmManager未運行服務
- 16. Android AlarmManager和服務問題
- 17. Android後臺服務和AlarmManager
- 18. AlarmManager或服務或其他?
- 19. 服務,IntentService,BroadcastReceiver或AlarmManager?
- 20. Android後臺服務與AlarmManager
- 21. AlarmManager服務調用不起作用
- 22. AlarmManager不調用後臺服務
- 23. AlarmManager廣播沒有收到
- 24. 使用沒有服務架構的silverlight
- 25. 使用sql沒有任何服務器
- 26. 使用reactdredx沒有服務器渲染
- 27. 沒有調用BroadcastReceiver的onReceiver,AlarmManager
- 28. 使用AlarmManager和廣播接收器啓動Android服務
- 29. 無法停止使用alarmManager開始的服務
- 30. 使用alarmManager和服務只在特定的時間段
把你的鏈接放在一個解決方案,我會檢查它。 – AndroidDev 2013-04-20 10:40:43