희망 너무 늦지 않으므로 너와 똑같은 문제가있다. 내 응용 프로그램은 내부 저장 파일에서 특정 간격 (30m/1h/2h/4h)으로 서버에 데이터를 전송해야했습니다. getActiveNetworkInfo()
의 경우 적절한 결과를 얻으려면 wifi를 깨우지 않아야합니다 (5 ~ 15 분 후에 잠자기 wifi가 꺼지기 때문).
/** Receiver for keeping the device awake */
public class WakeUpReceiver extends WakefulBroadcastReceiver {
// Constant to distinguish request
public static final int WAKE_TYPE_UPLOAD = 2;
// AlarmManager to provide access to the system alarm services.
private static AlarmManager alarm;
// Pending intent that is triggered when the alarm fires.
private static PendingIntent pIntent;
/** BroadcastReceiver onReceive() method */
@Override
public void onReceive(Context context, Intent intent) {
// Start appropriate service type
int wakeType = intent.getExtras().getInt("wakeType");
switch (wakeType) {
case WAKE_TYPE_UPLOAD:
Intent newUpload = new Intent(context, UploadService.class);
startWakefulService(context, newUpload);
break;
default:
break;
}
}
/** Sets alarms */
@SuppressLint("NewApi")
public static void setAlarm(Context context, int wakeType, Calendar startTime) {
// Set alarm to start at given time
alarm = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(context, WakeUpReceiver.class);
intent.putExtra("wakeType", wakeType);
pIntent = PendingIntent.getBroadcast(context, wakeType, intent,
PendingIntent.FLAG_UPDATE_CURRENT);
// For android 4.4+ the method is different
if (android.os.Build.VERSION.SDK_INT >=
android.os.Build.VERSION_CODES.KITKAT) {
alarm.setExact(AlarmManager.RTC_WAKEUP,
startTime.getTimeInMillis() + 5000, pIntent);
} else {
alarm.set(AlarmManager.RTC_WAKEUP,
startTime.getTimeInMillis() + 5000, pIntent);
}
// The + 5000 is for adding symbolic 5 seconds to alarm start
}
}
는 참고 public static void setAlarm(Context, int, Calendar)
기능은, 내가 사용 : 내가 전화를 해제 할 필요가있을 때, 나는 호출되는 WakefulBroadcastReceiver
이
첫째, 그것은 나에게 문제를 많이했다, 그러나 여기 내 솔루션이 작동하는 방법 알람을 설정하는 기능 (기본 애플리케이션 참조).
: 알람이 설정 한 후 전화가 다시 서비스를 실행 재부팅 그래서 만약
/** Service for uploading data to server */
public class UploadService extends Service {
private static final String serverURI = "http://your.server.com/file_on_server.php";
private Looper mServiceLooper;
private ServiceHandler mServiceHandler;
WifiLock wfl;
private Intent currentIntent;
private SharedPreferences sharedPrefs;
private int updateInterval;
private boolean continueService;
/** Service onCreate() method */
@Override
public void onCreate() {
super.onCreate();
// Initialize wifi lock
wfl = null;
// Initialize current Intent
currentIntent = null;
// Create separate HandlerThread
HandlerThread thread = new HandlerThread("SystemService",
Process.THREAD_PRIORITY_BACKGROUND);
thread.start();
// Get the HandlerThread's Looper and use it for our Handler
mServiceLooper = thread.getLooper();
mServiceHandler = new ServiceHandler(mServiceLooper);
// Get shared variables values if set
sharedPrefs = getSharedPreferences("serviceVars", MODE_PRIVATE);
updateInterval = sharedPrefs.getInt("sendInterval", 60); // in your case 5
continueService = sharedPrefs.getBoolean("bgServiceState", false);
}
/** Service onStartCommand() method */
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
// If continuing, set new alarm
if (continueService) {
Calendar nextStart = Calendar.getInstance();
nextStart.set(Calendar.SECOND, 0);
// Set alarm to fire after the interval time
nextStart.add(Calendar.MINUTE, updateInterval);
WakeUpReceiver.setAlarm(this, WakeUpReceiver.WAKE_TYPE_UPLOAD,
nextStart);
}
// Get current Intent and save it
currentIntent = intent;
// Acquire a wifi lock to ensure the upload process works
WifiManager wm = (WifiManager) getSystemService(Context.WIFI_SERVICE);
wfl = wm.createWifiLock(WifiManager.WIFI_MODE_FULL, "WifiLock");
if (!wfl.isHeld()) {
wfl.acquire();
}
// For each start request, send a message to start a job and give
// start ID so we know which request we're stopping when we finish
Message msg = mServiceHandler.obtainMessage();
msg.arg1 = startId;
mServiceHandler.sendMessage(msg);
// If service gets killed, it will restart
return START_STICKY;
}
/** Handler that receives messages from the thread */
private final class ServiceHandler extends Handler {
public ServiceHandler(Looper looper) {
super(looper);
}
/** Executes all service operations */
@Override
public void handleMessage(Message msg) {
// First wait for 5 seconds
synchronized (this) {
try {
wait(5 * 1000);
} catch (Exception e) {
e.printStackTrace();
}
}
// Start checking if internet is enabled
boolean hasInternet = false;
long endTime = System.currentTimeMillis() + 55 * 1000;
// Check every second (max 55) if connected
while (System.currentTimeMillis() < endTime) {
if (hasInternet(UploadService.this)) {
hasInternet = true;
break;
}
synchronized (this) {
try {
wait(1000);
} catch (Exception e) {
e.printStackTrace();
}
}
}
// Connected to internet or 60 (5 + 55) seconds passed
if (hasInternet) {
// Connect to server
connectToServer(serverURI, fileName);
} else {
// Can't connect, send message or something
}
// Stop service
stopSelf(msg.arg1);
}
}
/** Checks if phone is connected to Internet */
private boolean hasInternet(Context context) {
ConnectivityManager cm = (ConnectivityManager) context
.getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo ni = null;
if (cm != null) {
ni = cm.getActiveNetworkInfo();
}
return ni != null && ni.getState() == NetworkInfo.State.CONNECTED;
}
/** Service onDestroy() method */
@Override
public void onDestroy() {
// Release wifi lock
if (wfl != null) {
if (wfl.isHeld()) {
wfl.release();
}
}
// Release wake lock provided by BroadcastReceiver.
WakeUpReceiver.completeWakefulIntent(currentIntent);
super.onDestroy();
}
/** Performs server communication */
private void connectToServer(String serverUri, String dataFileName) {
// this function does my network stuff
}
/** Service onBind() method - Not used */
@Override
public IBinder onBind(Intent intent) {
return null;
}
}
내가 또한, BOOT
BroadcastReceiver
있습니다
다음으로, 서비스 자체는 Service
, IntentService
아니다
:
/** Receiver for (re)starting alarms on device reboot operations */
public class BootReceiver extends BroadcastReceiver {
WakeUpReceiver alarm = new WakeUpReceiver();
/** BroadcastReceiver onReceive() method */
@Override
public void onReceive(Context context, Intent intent) {
if (intent.getAction().equals("android.intent.action.BOOT_COMPLETED")) {
WakeUpReceiver.setAlarm(context, WakeUpReceiver.WAKE_TYPE_UPLOAD,
Calendar.getInstance());
}
}
}
마지막은 아니지만 적어도 주 Activity
에, 나는 시작 수신기하여 서비스를 시작합니다 나는 서비스를 중지 할 때
// Start upload service now
Calendar timeNow = Calendar.getInstance();
WakeUpReceiver.setAlarm(this, WakeUpReceiver.WAKE_TYPE_UPLOAD, timeNow);
// Enable BootReceiver to (re)start alarm on device restart
getPackageManager().setComponentEnabledSetting(
new ComponentName(this, BootReceiver.class),
PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
PackageManager.DONT_KILL_APP);
는, 나는 너무 BOOT
수신기를 중지
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<uses-permission android:name="android.permission.WAKE_LOCK" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.CHANGE_WIFI_STATE" />
<uses-permission android:name="android.permission.INTERNET" />
<receiver
android:name=".BootReceiver"
android:enabled="false" >
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED" />
</intent-filter>
</receiver>
<receiver android:name=".WakeUpReceiver" />
<service
android:name=".UploadService"
android:enabled="true"
android:label="ServerUpload"
android:launchMode="singleInstance" />
을 나는 생각 :
// Disable BootReceiver to (re)start alarm on device restart
getPackageManager().setComponentEnabledSetting(
new ComponentName(this, BootReceiver.class),
PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
PackageManager.DONT_KILL_APP);
또한, 명시 할 적절한 권한과 구성 요소를 추가하는 것을 잊지 마세요 이 모든 것을 다 커버했기 때문에 누군가가 문제를 해결할 수 있다면 기쁠 것입니다.