I am simply trying to have an onlick listen on an Edit text inside a TextInputLayout. It works but I need to click on the EditText twice for it to trigger I dont understand why. Here is my code:
xml:
<android.support.design.widget.TextInputLayout android:layout_width="fill_parent" android:layout_height="wrap_content" android:layout_marginTop="10dp"> <EditText android:id="@+id/start_date" android:layout_width="fill_parent" android:layout_height="wrap_content" android:ems="10" android:hint="Starting Date*: " android:inputType="textPersonName" /> </android.support.design.widget.TextInputLayout>
Listenner:
private void setListenners() { EditText startDate = (EditText) mView.findViewById(R.id.start_date); startDate.setOnClickListener(new View.OnClickListener() { @RequiresApi(api = Build.VERSION_CODES.N) @Override public void onClick(View v) { Calendar mcurrentDate=Calendar.getInstance(); int mYear = mcurrentDate.get(Calendar.YEAR); int mMonth = mcurrentDate.get(Calendar.MONTH); int mDay = mcurrentDate.get(Calendar.DAY_OF_MONTH); DatePickerDialog mDatePicker=new DatePickerDialog(getActivity(), new DatePickerDialog.OnDateSetListener() { @Override public void onDateSet(DatePicker datePicker, int year, int month, int day) { Log.d("DEBUG", "year: " + year + " month: " + month + " day: " + day); } },mYear, mMonth, mDay); mDatePicker.show(); } }); }
The primary use of a TextInputLayout is to act as a wrapper for EditText(or its descendant) and enable floating hint animations. Rule of Thumb : TextInputLayout should wrap TextInputEditText instead of the normal EditText.
You can use the TextInputLayout to display error messages according to the material design guidelines using the setError and setErrorEnabled methods. In order to show the error below the EditText use: TextInputLayout til = (TextInputLayout) findViewById(R. id.
In your xml code set focusable="false" , android:clickable="false" and android:cursorVisible="false" and this will make your EditText treat like non editable.
Set the attribute android:focusableInTouchMode
to false
android:focusableInTouchMode="false"
in your edittext
xml code.
Explanation, as from docs, android:focusableInTouchMode
is:
Boolean that controls whether a view can take focus while in touch mode. If this is true for a view, that view can gain focus when clicked on, and can keep focus if another view is clicked on that doesn't have this attribute set to true.
and the EditText
is true by default.
In other words: the first click will make the edittext
to gain focus and second click is the one that triggers the ClickListener
. So you should disable gaining focus on touch.
I found an alternative solution which suited my needs better than the other answer. Basically you set the onClickListener as normal, but you add an OnFocusChangedListener to pick up the first tap (when gaining focus). This only activates in touch mode so doesn't affect keyboard navigation.
You don't need to set any XML attributes related to focus, just use the following code (it's kotlin btw):
editText.setOnFocusChangeListener { view, isFocused -> if (view.isInTouchMode && isFocused) { view.performClick() // picks up first tap } } editText.setOnClickListener { showDatePicker() // the actual thing you want to do }
This method has the advantage that the view will remain focused (and if you are using a TextInputLayout.OutlinedBox
style, it will remain highlighted) even after the DatePicker is dismissed. This does not happen when you set focusableInTouchMode = false
.
Once the view is focused, future taps will trigger only the OnClickListener, so it won't be called again by the FocusChangeListener
calling performClick()
. (I checked this with the debugger on API 29)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With