The
TimePicker
updates the one-line
TextView
.
The “Now”
Button
updates the
TimePicker
.
This example has a
TimePicker
without a
TimePickerDialog
.
The
TimePicker
tutorial
has a
TimePicker
with a
TimePickerDialog
.
Here is
my example
of a
TimePickerDialog
.
The
TextView
has to be
final
in order to be mentioned in
onTimeChanged
.
The
TimePicker
had to be
final
in order to be mentioned in
onClick
.
The
hour
passed to
onTimeChanged
is a 24-hour hour.
onTimeChanged
will not be called if the
TimePicker
is changed to the same time that it currently holds.
The time displayed the
TextView
is formatted in 12- or 24-hour format,
depending on the setting set by the Android Settings app.
Warning:
the
getTimeFormat
method of class
android.text.format.DateFormat
java.text.DateFormat
.DateFormat
s
are two different classes.
textView.setText(DateFormat.getTimeFormat(TimePickerActivity.this).format(calendar.getTime()));to
java.text.DateFormat dateFormat = DateFormat.getTimeFormat(TimePickerActivity.this)); textView.setText(dateFormat.format(calendar.getTime()));?
Button
and
TextView
have
android:layout_width="wrap_content"
rather than the usual
android:layout_width="fill_parent"
in
main.xml
,
we were able to center them horizontally with
android:layout_gravity="center_horizontal"
.
What happens when you remove the
android:layout_gravity="center_horizontal"
?TimePicker
automatically go into 24-hour mode when you chnage the settings in the Settings
app,
or do you have to call
is24HourFormat
and
setIs24HourView
manually?Thread
that will update the
TextView
once per second.
A
Thread
object has a method named
run
.
Create the following non-nested class in the file
TimePickerActivity.java
.
The
run
method
sends
a
Message
,
once per second, to the
Handler
that is plugged into the
Thread
.
When the
Handler
receives the
Message
,
the
Handler
updates the
TextView
.
Why do we need a separate
Handler
object?
Well, the Android UI is single-threaded.
That means a
TextView
can be written only by the
Thread
that created the
TextView
.
But the
TextView
and the
Handler
were both created by the
onCreate
method of the
Activity
,
so they both belong to the same thread.
See main use #2 of a
Handler
.
final class MyThread extends Thread { final Handler handler; final Calendar calendar = Calendar.getInstance(); MyThread(Handler handler) { this.handler = handler; } @Override public void run() { for (;;) { try { //1000 milliseconds == 1 second Thread.sleep(1000); } catch (InterruptedException interruptedException) { Log.e("ERROR", "sleep interrupted", interruptedException); } final Message message = handler.obtainMessage(); //Get an empty Message. calendar.setTime(new Date()); message.arg1 = calendar.get(Calendar.MINUTE); //Fill it up. message.arg2 = calendar.get(Calendar.SECOND); //Send the mesage to the Handler. //Calls handleMessage, below. handler.sendMessage(message); } } }
At the end of
onCreate
,
create the
Handler
and the
Thread
.
Plug the
Handler
into the
Thread
and
start
the
Thread
.
%02d
final Handler handler = new Handler() { @Override public void handleMessage(Message message) { textView.setText(String.format("%d:%02d", message.arg1, message.arg2)); } }; final MyThread myThread = new MyThread(handler); myThread.start();
arg1
occupies 32 bits.
Encode the hour in the 16 high-order bits,
the minute in the 16 low-order bits.
//in the run method of MyThread message.arg1 = calendar.get(Calendar.HOUR_OF_DAY) << 16 | calendar.get(Calendar.MINUTE)
//in the handleMessage method of the Handler textView.setText(String.format("%d%02d:%02d", message.arg1 >>> 16, //prevent sign extension message.arg1 & 0xFF, //mask off the 16 high-order bits message.arg2 ));
obj
field of the
Message
instead of
arg1
and
arg2
.
Create the following non-nested class in the file
TimePickerActivity.java
.
No reference to
Master
and Commander
is intended.
final class Hms { public int hour; public int minute; public int second; Hms(int hour, int minute, int second) { this.hour = hour; this.minute = minute; this.second = second; } }
//in the run method of MyThread message.obj = new Hms( calendar.get(Calendar.HOUR_OF_DAY), calendar.get(Calendar.MINUTE), calendar.get(Calendar.SECOND) );
//in the handleMessage method of the Handler textView.setText(String.format("%d:%02d:%02d", ((Hms)message.obj).hour, ((Hms)message.obj).minute, ((Hms)message.obj).second ));
post
method of class
View
to let the second thread communicate with the main thread?