Android 如何在按下按钮后每 10 分钟重复一次方法并在按下另一个按钮时结束它

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/10221996/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-20 02:55:07  来源:igfitidea点击:

How do I repeat a method every 10 minutes after a button press and end it on another button press

android

提问by X-Man

I am writing an Android app that retrieves the phone's current location and sends it too a webserver. I want to be able to press a start button and have the app continue to retrieve and send the location at a predetermined interval (say every 10 minutes) and then have it stop on another button press.

我正在编写一个 Android 应用程序,用于检索手机的当前位置并将其发送到网络服务器。我希望能够按下一个开始按钮,让应用程序继续以预定的时间间隔(比如每 10 分钟)检索和发送位置,然后在按下另一个按钮时停止。

Here is the code for my buttons:

这是我的按钮的代码:

public void onCreate(Bundle savedInstanceState) {

    super.onCreate(savedInstanceState);
    setContentView(R.layout.main);

   startButton.setOnClickListener(new OnClickListener() {
    @Override
    //When the button is clicked
    public void onClick(View v) {
            finishButton.setEnabled(true);
            startButton.setEnabled(false);

            //Loops every 10mins
            pingCurrentLocation();

        }
    });

  finishButton.setOnClickListener(new OnClickListener() {
    @Override
    //When the button is clicked
    public void onClick(View v) {
            startButton.setEnabled(true);
            finishButton.setEnabled(false);

            pingCurrentLocation();

        }
    });  
}

pingCurrentLocation is the function that gets the location and sends it.

pingCurrentLocation 是获取位置并发送位置的函数。

I know that using an AlarmManager would probably achieve what I want but I have been unable to make sense of any of it. Are there any clear steps or templates that will work in my situation.

我知道使用 AlarmManager 可能会实现我想要的,但我一直无法理解其中的任何一个。是否有任何明确的步骤或模板适用于我的情况。

回答by coderplus

Create a BroadcastReceiver

创建一个 BroadcastReceiver

public class AlarmReceiver extends BroadcastReceiver
{   

 @Override
 public void onReceive(Context context, Intent intent)
  {   
    //get and send location information
  }
}

and add the same to your AndroidManifestso that the Receiver is registered

并将相同的内容添加到您的AndroidManifest以便注册接收器

<receiver
    android:name="com.coderplus.AlarmReceiver"
    android:exported="false">
</receiver>

Now you can set a repeating alarm from your Activitywhich will invoke the receiver every 10 minutes:

现在你可以设置一个重复的闹钟,Activity每 10 分钟调用一次接收器:

AlarmManager alarmManager=(AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(context, AlarmReceiver.class);
PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 0, intent, 0);
alarmManager.setRepeating(AlarmManager.RTC_WAKEUP,System.currentTimeMillis(),600000,
                                                                      pendingIntent);

and to cancel the alarm, call cancel()on the AlarmManagerusing an equivalent PendingIntent

并取消报警,称cancel()AlarmManager使用等效PendingIntent

AlarmManager alarmManager=(AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(context, AlarmReceiver.class);
PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 0, intent, 0);
alarmManager.cancel(pendingIntent);


or if you don't want to use AlarmManager/ BroadcastReceiver, then something like this will help you out. Before you go for it, check - difference between timer and alarmmanager

或者如果你不想使用AlarmManager/ BroadcastReceiver,那么像这样的东西会帮助你。在你去之前,检查 -计时器和警报管理器之间的区别

private class MyTimerTask extends TimerTask {
    @Override
    public void run() {           
      //get and send location information 
    }
}

initialize the Timerand Timertask:

初始化TimerTimer任务:

Timer myTimer = new Timer();
MyTimerTask myTimerTask= new MyTimerTask();

Stopping or starting the Timer

停止或启动 Timer

//to Stop
myTimer.cancel();
//to start
myTimer.scheduleAtFixedRate(myTimerTask, 0, 600000); //(timertask,delay,period)

Refer http://developer.android.com/reference/java/util/TimerTask.html

参考 http://developer.android.com/reference/java/util/TimerTask.html

http://developer.android.com/reference/java/util/Timer.html

http://developer.android.com/reference/java/util/Timer.html

回答by user370305

Use Android-TimerTaskor Android-AlarmManagerfor sending location data to every 10 minutes. Look at this SO question Track Gps At every 10 minutes using timer in androidalso this one Good way of getting the user's location in Android

使用Android-TimerTaskAndroid-AlarmManager每 10 分钟发送一次位置数据。看看这个 SO 问题Track Gps At every 10 minutes using timer in android andthis one Good way to get the user's location in Android in Android

TimerTask:

定时器任务:

The TimerTaskclass represents a task to run at a specified time. The task may be run once or repeatedly.

TimerTask类代表一个任务在指定时间运行。任务可以运行一次或重复运行。

回答by drulabs

Here is what I did.

这是我所做的。

created an alarm manager object first, and set the repeating timer

首先创建一个警报管理器对象,并设置重复计时器

AlarmManager alarmMgr = alarmMgr=(AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
Intent alarmIntent = alarmIntent = new Intent("AlarmIntentReceiver"); 
PendingIntent pendingAlarmIntent = pendingAlarmIntent = PendingIntent.getBroadcast(context.getApplicationContext(), 0, alarmIntent, 0);
alarmMgr.setRepeating(AlarmManager.ELAPSED_REALTIME_WAKEUP, 30*1000, 3*60*1000,  pendingAlarmIntent); //start in 30 secs and rest in 3 mins interval

Created an activity based on that intent name that will capture the intent and execute it's code in the interval specified, you can also create a broadcast receiver if you like.

根据该意图名称创建一个活动,该活动将捕获意图并在指定的时间间隔内执行其代码,如果您愿意,您还可以创建一个广播接收器。

To cancel it in your button click event. Write this

在你的按钮点击事件中取消它。写这个

alarmMgr.cancel(pendingAlarmIntent);

回答by Sandip Jadhav

You can start a service which will check for user location & send it to your specified web address as mentioned below.

您可以启动一项服务,该服务将检查用户位置并将其发送到您指定的网址,如下所述。

you can get more information about service here

您可以在此处获取有关服务的更多信息

public class TaxiLocationUpdator extends Service{
    Location location;
    Timer timer = new Timer();
    private final Handler handler = new Handler();
    Intent intent;

    @Override
    public IBinder onBind(Intent arg0) {
        // TODO Auto-generated method stub
        return null;
    }

    public void  onCreate(){
        super.onCreate();
        updateNotification();
    }

    //int onStartCommand(Intent intent, int flags, int startId) 
    public void onStart(Intent intent,int startId){
        super.onStart(intent, startId);
        handler.removeCallbacks(sendUpdatesToUI);
            handler.postDelayed(sendUpdatesToUI, 1000); // 1 second
        Log.v("Location Servics", "Start Service");
    }

     private Runnable sendUpdatesToUI = new Runnable() {
            public void run() {
                DisplayLoggingInfo();           
                    handler.postDelayed(this, 15000); // 60 seconds here you can give your time
            }
        };    

    public void onDestroy(){
        super.onDestroy();
        Log.v("Location Servics", "Destroy Service");
    }

    public boolean isOnline(){
            ConnectivityManager cm = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
            NetworkInfo netInfo = cm.getActiveNetworkInfo();
            boolean isconnected;
            if (netInfo==null || !netInfo.isConnected())
            isconnected=false;
            else
            isconnected=true;
            Log.v("isOnliNe",isconnected+"");
            return isconnected;
        }

    protected void updateNotification() {
             LocationManager lm = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
             LocationListener locationListener = new MyLocationlistener();

             lm.requestLocationUpdates(LocationManager.GPS_PROVIDER, normallocationwait, 0.250f, locationListener);
             location = lm.getLastKnownLocation(LocationManager.GPS_PROVIDER);
       }

       private class MyLocationlistener implements LocationListener {

         public void onLocationChanged(Location location){
             if(location!=null){
                 if(location.hasAccuracy()){
                       dumpLocation(location);
                 }else{
                       dumpLocation(location);
                }
             } 
         }

         public void onProviderDisabled(String provider){
             Log.v("Loc Update","\nProvider disabled: " + provider);
         }

         public void onProviderEnabled(String provider){
             Log.v("Loc Update","\nProvider enabled: " + provider);
         }

         public void onStatusChanged(String provider, int status, Bundle extras){
             Log.v("Loc Update","\nProvider status changed: " + provider + ", status="
                        + status + ", extras=" + extras);
         }

         private void dumpLocation(Location location) {
                 if (location == null)
                        Log.v("Loc Update","\nLocation[unknown]");
                 else{
                         Log.v("Loc Update","\n" + location.toString());
                         Log.v("Demo", location.toString());
                                 String url  = Your url;
                         Toast.makeText(getBaseContext(), "Location Update", Toast.LENGTH_SHORT).show();
                         if(isOnline()){
                            HttpClient httpclient = new DefaultHttpClient();
                            HttpPost httppost = new HttpPost(url);
                            try {
                                HttpResponse response = httpclient.execute(httppost);
                                Log.v("Message", response.toString());
                              } catch (ClientProtocolException e) {
                                  Log.e("Sending Message",e.getMessage().toString());
                              } catch (IOException e) {
                                  Log.e("Sending Message",e.getMessage().toString());
                            }
                     }
                } 
          }

         public boolean isOnline(){
            ConnectivityManager cm = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
            NetworkInfo netInfo = cm.getActiveNetworkInfo();
            boolean isconnected;
            if (netInfo==null || !netInfo.isConnected())
            isconnected=false;
            else
            isconnected=true;
            Log.v("isOnliNe",isconnected+"");
            return isconnected;
         }
     }
}

回答by Zacharias Manuel

Use a thread and a handler

使用线程和处理程序

   Handler alarmCheckHandler = new Handler() {

        @Override
        public void handleMessage(Message msg) {
            super.handleMessage(msg);

                System.out.println("getting message from alarm thread");
                //Call your function for ping



    };
Thread alarmCheckThread = new Thread() {
        public void run() {
            int i = 0;
            synchronized (this) {
                while (checkflag) {
                    i++;
                    try {
                        sleep(1000);
                    } catch (InterruptedException e) {
                        // TODO Auto-generated catch block
                        e.printStackTrace();
                    }
                    if (i == 600) {
                        alarmCheckHandler.sendMessage(alarmCheckHandler
                                .obtainMessage());
                        i = 0;
                    }

                }
                System.out.println("End of unlimited while loop reched");
            }
        }
    };

For start call

对于开始呼叫

alarmCheckThread.start();

For stop call

停止呼叫

alarmCheckThread.interrupt();