Chronometer. Cliclo de vida I (finish())

De MediaWiki
Ir a la navegación Ir a la búsqueda

Introdución

  • Un control Chronometer implementa en Android un cronómetro simple.
  • Iníciase có método start().
  • Párase có método stop(). Pero ... el segue contando por detrás. Isto é, se se executa de novo start() sen parámetros porá o cronómetro no mesmo tempo que se non se parase.


  • Cando se chama a start(), o control colle o tempo que leva acceso o móbil (elapsedRealtime()) como tempo base e vai contando dende aí.
Se non se lle dá un tempo base el colle o tempo no cal se chama a start().



  • A clase Chronometer herda directamente da clase View.
  • Para establecer os valores de tempos base apoiámonos na clase SystemClock.


Caso práctico

Se non o temos creado antes, crea un paquete de nome UI como un subpaquete do teu paquete principal.
Dentro do paquete UI, crearemos un novo paquete de nome: Chonometers.



  • Dentro do paquete Chonometers crear unha nova 'Empty Activity' de nome: UD02_01_Chonometer de tipo Launcher e sen compatibilidade.
Modifica o arquivo AndroidManifiest.xml e engade unha label á activity como xa vimos na creación do proxecto base.





XML do Layout

  • Observar como se crea o control Chronometer e os métodos aos que chaman os botóns.
 1 <?xml version="1.0" encoding="utf-8"?>
 2 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
 3     android:layout_width="match_parent"
 4     android:layout_height="match_parent"
 5     android:orientation="vertical" >
 6 
 7     <TextView
 8         android:id="@+id/tvAutodestr_UD02_01_Chonometer"
 9         android:layout_width="wrap_content"
10         android:layout_height="wrap_content"
11         android:text="Autodestrucción en: ?? seg" />
12 
13     <Chronometer
14         android:id="@+id/chrCronometro_UD02_01_Chonometer"
15         android:layout_width="wrap_content"
16         android:layout_height="wrap_content"
17         android:layout_gravity="center_horizontal"
18         android:textSize="20sp" />
19 
20     <LinearLayout
21         android:layout_width="match_parent"
22         android:layout_height="match_parent"
23         android:gravity="center_horizontal"
24         android:orientation="horizontal" >
25 
26         <Button
27             android:id="@+id/btStart_UD02_01_Chonometer"
28             android:layout_width="wrap_content"
29             android:layout_height="wrap_content"
30             android:text="Start" />
31 
32         <Button
33             android:id="@+id/btStop_UD02_01_Chonometer"
34             android:layout_width="wrap_content"
35             android:layout_height="wrap_content"
36             android:text="Stop" />
37     </LinearLayout>
38 
39 </LinearLayout>



Código Java

 1 package es.cursoandroid.cifprodolfoucha.aprendiendo.UI.Chronometers;
 2 
 3 import android.app.Activity;
 4 import android.os.Bundle;
 5 import android.os.SystemClock;
 6 import android.view.View;
 7 import android.widget.Button;
 8 import android.widget.Chronometer;
 9 import android.widget.TextView;
10 
11 import es.cursoandroid.cifprodolfoucha.aprendiendo.R;
12 
13 public class UD02_01_Chronometer extends Activity {
14 
15     private int tempoAutodestrucion; // Non podemos declarala final xa que se modifica o seu valor. Ao ter unha referencia a ela dentro da clase anónima OnChronometerTickListener, temos que declaralo a nivel de clase
16     private Chronometer crono;
17 
18     private void xestionarEventos(){
19         final TextView tvAutodestrucion;
20 
21         // Eventos do crono
22         crono = (Chronometer) findViewById(R.id.chrCronometro_UD02_01_Chonometer);
23         tvAutodestrucion = (TextView) findViewById(R.id.tvAutodestr_UD02_01_Chonometer);    // O poñemos aquí xa que o método onChronometerTick execútase moitas veces
24         crono.setOnChronometerTickListener(new Chronometer.OnChronometerTickListener() {
25             @Override
26             public void onChronometerTick(Chronometer chronometer) {
27                 // TODO Auto-generated method stub
28 
29                 long tempoPasado = SystemClock.elapsedRealtime()
30                         - chronometer.getBase();
31                 int tempoSeg = (int) tempoPasado / 1000;
32                 if (tempoSeg == tempoAutodestrucion)
33                     finish();
34 
35                 tvAutodestrucion.setText("Autodestrucción en: "
36                         + (tempoAutodestrucion - tempoSeg) + " seg");
37             }
38         });
39 
40         // Eventos botón start
41         Button btStart = findViewById(R.id.btStart_UD02_01_Chonometer);
42         btStart.setOnClickListener(new View.OnClickListener() {
43             @Override
44             public void onClick(View v) {
45                 tempoAutodestrucion = 20;
46                 crono.setBase(SystemClock.elapsedRealtime());
47                 crono.start();
48             }
49         });
50 
51         //Eventos botón stop (non temos por que declarar unha variable)
52         ((Button)findViewById(R.id.btStop_UD02_01_Chonometer)).setOnClickListener(new View.OnClickListener() {
53             @Override
54             public void onClick(View v) {
55                 crono.stop();
56             }
57         });
58 
59     }
60     @Override
61     protected void onCreate(Bundle savedInstanceState) {
62         super.onCreate(savedInstanceState);
63         setContentView(R.layout.activity_ud02_01__chronometer);
64 
65         xestionarEventos();
66     }
67 
68 
69 }
  • Liñas 40-49: Xestionamos o evento de Click sobre o botón start:
  • Liña 45: Definimos o tempo para a autodestrucción da Activity. Cando se vexan os menús, veremos que este valor podería ser configurado polo usuario que usa a aplicación, como unha opción da mesma.
  • Liña 46: establécese o tempo base a partir do cal o cronómetro comeza a contar. SystemClock.elapsedRealtime(): devolve o tempo, en milisegundos, que leva aceso o móbil
  • Liña 47: o cronómetro comeza a contar, non dende cero, senón dende o tempo tomado como base (o tempo que leva acceso o móbil).
  • Liñas 51-57: Xestionamos o evento de Click sobre o botón stop:
  • Liña 55: párase o cronómetro.
  • Liñas 21-38: Xestionamos o listener no cronómetro que se chama cada vez que hai un cambio no seu valor:
  • Liña 24: establécese o Listener do cronómetro. Este método vai ser chamado cada vez que o cronómetro cambia de valor.
  • Liñas 29 e 30: O tempo que pasou dende que se iniciou o cronómetro é a diferencia entre o tempo que leva acceso o dispositivo e o tempo no cal se iniciou o cronómetro.
  • Liña 31: Tempo en segundos.
  • Liña 33: Se chegamos ao tempo para autodestrucción hai que matar a Activity. Sería o mesmo que se prememos o botón da botonera "Retroceso ou Back".

Ciclo de vida dunha actividade

  • Afondarase máis adiante sobre o ciclo de vida dunha actividade.
  • Unha actividade desde que se lanza pasa por moitos estados.
  • Cando unha actividade non está en primeira liña da pantalla non está destruída senón que está en estado de Stop (Oculta) esperando na pila a ser chamada, ou se está moi abaixo na pila e se precisan os seus recursos entón o sistema pode destruíla.

00 basic-lifecycle.png

  • No noso exemplo a actividade destrúese explicitamente se o cronómetro chega a un tempo determinado
  • Para iso úsase o método finish().
  • Ver liña 33 do código.




-- Ángel D. Fernández González e Carlos Carrión Álvarez -- (2015).