25

我想在单击编辑文本时打开一个日历。之后,我想在编辑文本中设置用户从日历中选择的日期。问题是,只有当我第二次单击 EditText 时,日历才会打开。请帮我解决问题(why calendar don't open for the first time)。

编辑文本XML 代码

<EditText
            android:id="@+id/dateofBirth"
            android:layout_width="290dp"
            android:layout_height="wrap_content"
            android:layout_marginLeft="5dp"
            android:layout_marginTop="10dp"
            android:maxLines="1"
            android:hint="dd/mm/yyyy" />

活动代码

public void informationPopUp() {
        final Dialog dialog= new Dialog(MainActivity.this,R.style.Dialog_Fullscreen);
        dialog.setContentView(R.layout.details_dialog); 
        dateofBirth = (EditText)dialog.findViewById(R.id.dateofBirth);

        dialog.show();
         myCalendar = Calendar.getInstance();

       final DatePickerDialog.OnDateSetListener date = new DatePickerDialog.OnDateSetListener() {

            @Override
            public void onDateSet(DatePicker view, int year, int monthOfYear,
                    int dayOfMonth) {
                // TODO Auto-generated method stub
                myCalendar.set(Calendar.YEAR, year);
                myCalendar.set(Calendar.MONTH, monthOfYear);
                myCalendar.set(Calendar.DAY_OF_MONTH, dayOfMonth);
                updateLabel();
            }


        };

        dateofBirth.setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                showDialog(DATE_DIALOG_ID);
              }
        });

    }
     private void updateLabel() {
         String myFormat = "MM/dd/yy"; //In which you need put here
         SimpleDateFormat sdf = new SimpleDateFormat(myFormat, Locale.US);
         dateofBirth.setText(sdf.format(myCalendar.getTime()));
     }

     protected Dialog onCreateDialog(int id) {
            final Calendar now = Calendar.getInstance();

            switch (id) {
            case DATE_DIALOG_ID:
                // set date picker as current date
                DatePickerDialog _date =   new DatePickerDialog(this, date,myCalendar
                        .get(Calendar.YEAR), myCalendar.get(Calendar.MONTH),
                        myCalendar.get(Calendar.DAY_OF_MONTH)){
                    @Override

                    public void onDateChanged(DatePicker view, int year, int monthOfYear, int dayOfMonth){   

                        if (year > now.get(Calendar.YEAR))

                            view.updateDate(myCalendar
                                    .get(Calendar.YEAR), myCalendar
                                    .get(Calendar.MONTH), myCalendar.get(Calendar.DAY_OF_MONTH));

                        if (monthOfYear > now.get(Calendar.MONTH) && year == now.get(Calendar.YEAR))
                            view.updateDate(myCalendar
                                    .get(Calendar.YEAR), myCalendar
                                    .get(Calendar.MONTH), myCalendar.get(Calendar.DAY_OF_MONTH));

                        if (dayOfMonth > now.get(Calendar.DAY_OF_MONTH) && year == now.get(Calendar.YEAR) && 
                                monthOfYear == now.get(Calendar.MONTH))
                            view.updateDate(myCalendar
                                    .get(Calendar.YEAR), myCalendar
                                    .get(Calendar.MONTH), myCalendar.get(Calendar.DAY_OF_MONTH));
                            }
                };
                return _date;
            }
            return null;
        } 

我不明白我做错了什么。请提出解决方案。

4

20 回答 20

38

我会尝试解决您的问题,但我不完全确定第一个原因。

  1. 仅在第二次单击时打开日历是因为您使用的是编辑文本。第一次单击时,您的编辑文本将获得焦点。然后第二次点击只调用 onClickListener。

    如果您不期待手动编辑日期集(使用键盘),那么为什么不使用 TextView 来显示选定的日期呢?

  2. 由于您没有在代码中设置 DateSetListener ,因此发生了日期未在 editText 中更新的问题。您需要设置它以通知系统设置了日期。DateChange 侦听器仅在您更改日期时返回日期,并且您似乎没有在 EditText 中设置日期。

试试这个代码:

            Calendar cal = Calendar.getInstance(TimeZone.getDefault());
            DatePickerDialog datePicker = new DatePickerDialog(this,
                R.style.AppBlackTheme,
                datePickerListener,
                cal.get(Calendar.YEAR), 
                cal.get(Calendar.MONTH),
                cal.get(Calendar.DAY_OF_MONTH));

            datePicker.setCancelable(false);
            datePicker.setTitle("Select the date");

            return datePicker;
        }
    } catch (Exception e) {
        showMsgDialog("Exception",
            "An error occured while showing Date Picker\n\n"
            + " Error Details:\n" + e.toString(), "OK");
    }
    return null;
}


private DatePickerDialog.OnDateSetListener datePickerListener = new DatePickerDialog.OnDateSetListener() {

    // when dialog box is closed, below method will be called.
    public void onDateSet(DatePicker view, int selectedYear, int selectedMonth, int selectedDay) {
        String year1 = String.valueOf(selectedYear);
        String month1 = String.valueOf(selectedMonth + 1);
        String day1 = String.valueOf(selectedDay);
        TextView tvDt = (TextView) findViewById(R.id.tvDate);
        tvDt.setText(day1 + "/" + month1 + "/" + year1);
    }
};

在此,我将日期更新为 ID 为“tvDate”的 TextView。我建议使用 TextView 而不是 EditText 并尝试此代码。

更新

如果您需要使用 EditText 并在第一次单击时加载日历,请尝试将 onFocusListner 设置为 editText 而不是 onClickListner。

editText.setOnFocusChangeListener(new OnFocusChangeListener() {
    @Override
    public void onFocusChange(View v, boolean hasFocus) {
        if(hasFocus) {
           // Show your calender here 
        } else {
           // Hide your calender here
        }
    }
});
于 2013-08-16T07:27:23.610 回答
15

将此添加到您的编辑文本中以在第一次单击时打开日期选择器。 android:focusable="false"

于 2015-06-12T12:51:50.537 回答
8
public class MainActivity extends Activity  {

 private Calendar cal;
 private int day;
 private int month;
 private int year;
 private EditText et;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

     et= (EditText) findViewById(R.id.edittext1);
      cal = Calendar.getInstance();
      day = cal.get(Calendar.DAY_OF_MONTH);
      month = cal.get(Calendar.MONTH);
      year = cal.get(Calendar.YEAR);


     et.setText(day+"/"+month+"/"+"/"+year);



      et.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(View v) {

            DateDialog(); 

        }
    });
     }


public void DateDialog(){

    OnDateSetListener listener=new OnDateSetListener() {

        @Override
        public void onDateSet(DatePicker view, int year, int monthOfYear,int dayOfMonth)
        {

         et.setText(dayOfMonth+"/"+monthOfYear+"/"+year);

        }};

    DatePickerDialog dpDialog=new DatePickerDialog(this, listener, year, month, day);
    dpDialog.show();

}





}
于 2014-05-29T13:06:15.783 回答
6

在您的 xml 中,将可聚焦设置为 false

android:focusable="false"
于 2018-01-05T04:11:58.193 回答
5

只做这个

//Open the DatePicker dialgo in one click and also hide the soft keyboard.
youEditText.setInputType(InputType.TYPE_NULL);
youEditText.requestFocus();
于 2014-10-01T11:01:10.633 回答
3

使用 setOnFocusChangeListener 而不是 OnCLickListner 以下代码是我用于相同目的的示例。

editText_dob.setOnFocusChangeListener(new View.OnFocusChangeListener() {
        @Override
        public void onFocusChange(View v, boolean hasFocus) {
            if(hasFocus){
                hideSoftKeyboard(RegisterationActivity.this);
                editText_dob.setRawInputType(InputType.TYPE_CLASS_TEXT);
                setDate(editText_dob);
            }
        }
    });
于 2016-10-06T06:44:30.147 回答
3

首先在您的活动中定义这些变量

    import android.app.AlertDialog;
    import android.app.DatePickerDialog;
    import android.app.TimePickerDialog;
    import android.content.Context;
    import android.content.DialogInterface;
    import android.util.Log;
    import android.view.View;
    import android.widget.DatePicker;
    import android.widget.TimePicker;

    import java.text.DateFormat;
    import java.text.ParseException;
    import java.text.SimpleDateFormat;
    import java.util.Calendar;
    import java.util.Date;

public class MainActivity extends Activity  {

    private int mYear, mMonth, mDay, mHour, mMinute;

然后使用这些方法:

1) 用于打开日期选择器模式

            public void openDatePicker() {
                // Get Current Date
                final Calendar c = Calendar.getInstance();
                mYear  = c.get(Calendar.YEAR);
                mMonth = c.get(Calendar.MONTH);
                mDay   = c.get(Calendar.DAY_OF_MONTH);
                //launch datepicker modal
                DatePickerDialog datePickerDialog = new DatePickerDialog(this,
                        new DatePickerDialog.OnDateSetListener() {
                            @Override
                            public void onDateSet(DatePicker view, int year, int monthOfYear, int dayOfMonth) {
                                Log.d(APIContanst.LOG_APP, "DATE SELECTED "+dayOfMonth + "-" + (monthOfYear + 1) + "-" + year);
                                //PUT YOUR LOGING HERE
                                //UNCOMMENT THIS LINE TO CALL TIMEPICKER
                               //openTimePicker();
                            }
                        }, mYear, mMonth, mDay);
                datePickerDialog.show();
            }

2) 用于打开时间选择器模式

            public void openTimePicker() {
                // Get Current Time
                final Calendar c = Calendar.getInstance();
                mHour            = c.get(Calendar.HOUR_OF_DAY);
                mMinute          = c.get(Calendar.MINUTE);
                //launch timepicker modal
                TimePickerDialog timePickerDialog = new TimePickerDialog(this,
                        new TimePickerDialog.OnTimeSetListener() {
                            @Override
                            public void onTimeSet(TimePicker view, int hourOfDay, int minute) {
                                Log.d(APIContanst.LOG_APP, "TIME SELECTED "+hourOfDay + "-" + minute + "-");
                            //PUT YOUR LOGIC HERE
                            }
                        }, mHour, mMinute, false);
                timePickerDialog.show();
            }

您也可以结合这两种方法在关闭日期选择器后打开时间选择器。

这些功能不需要使用插件

于 2016-11-03T16:37:37.677 回答
2

试试这个代码 100% 有效

在 ONCREATE 中写入

et_dob.setOnClickListener(new View.OnClickListener() {

        @Override
        public void onClick(View v) {
            showDialog(DATE_DIALOG_ID);
        }

    });
    final Calendar calendar = Calendar.getInstance();
    DateFormat df = new SimpleDateFormat("yyyy-MM-dd");
    if (et_dob.getText().toString() != null) {
        try {
            calendar.setTime(df.parse(et_dob.getText().toString()));
        } catch (java.text.ParseException e1) {
            // TODO Auto-generated catch block
            e1.printStackTrace();
        }
        mYear = calendar.get(Calendar.YEAR);
        mMonth = calendar.get(Calendar.MONTH);
        mDay = calendar.get(Calendar.DAY_OF_MONTH);
        SimpleDateFormat month_date = new SimpleDateFormat("MMM");
        month = month_date.format(calendar.getTime());
    } else {
        mYear = calendar.get(Calendar.YEAR);
        mMonth = calendar.get(Calendar.MONTH);
        mDay = calendar.get(Calendar.DAY_OF_MONTH);
        SimpleDateFormat month_date = new SimpleDateFormat("MMM");
        month = month_date.format(calendar.getTime());
    }

    if (cal_currentTime.compareTo(calendar) > 0)
        updateDisplay();

并在您的班级中粘贴剩余的代码

static final int DATE_DIALOG_ID = 1;
private int mYear;
private int mMonth;
private int mDay;
private String month;
private String dateOfBirth;


@Override
protected Dialog onCreateDialog(int id) {
    switch (id) {
    case DATE_DIALOG_ID:
        return new DatePickerDialog(this, mDateSetListener, mYear, mMonth,
                mDay);
    }
    return null;
}

@Override
protected void onPrepareDialog(int id, Dialog dialog) {
    switch (id) {
    case DATE_DIALOG_ID:
        ((DatePickerDialog) dialog).updateDate(mYear, mMonth, mDay);
        break;
    }
}

private DatePickerDialog.OnDateSetListener mDateSetListener = new DatePickerDialog.OnDateSetListener() {

    public void onDateSet(DatePicker view, int year, int monthOfYear,
            int dayOfMonth) {
        mYear = year;
        mMonth = monthOfYear;
        mDay = dayOfMonth;

        String dateSetter = (new StringBuilder().append(mYear).append("-")
                .append(mMonth + 1).append("-").append(mDay).append(""))
                .toString();
        final Calendar cal = Calendar.getInstance();
        DateFormat df = new SimpleDateFormat("yyyy-MM-dd");
        if (dateSetter != null) {
            try {
                cal.setTime(df.parse(dateSetter));
            } catch (java.text.ParseException e1) {
                // TODO Auto-generated catch block
                e1.printStackTrace();
            }
            SimpleDateFormat month_date = new SimpleDateFormat("MMM");
            month = month_date.format(cal.getTime());
        }

        if (cal_currentTime.compareTo(cal) > 0)
            updateDisplay();
        else
            Toast.makeText(context, "Choose Proper date format",
                    Toast.LENGTH_SHORT).show();
    }
};

加载它以编辑文本

private void updateDisplay() {
    dateOfBirth = (new StringBuilder()
            // Month is 0 based so add 1
            .append(mYear).append("-").append(mMonth + 1).append("-")
            .append(mDay).append("")).toString();
    et_dob.setText(new StringBuilder()
            // Month is 0 based so add 1
            .append(mDay).append("-").append(month).append("-")
            .append(mYear));
}
于 2013-08-16T06:36:52.510 回答
2

只需在您的 EditText 中使用它

    android:focusable="false"
于 2016-04-21T12:03:26.680 回答
1

将此添加到您的 EditText xml 文件中:

    android:clickable="false" 
    android:cursorVisible="false" 
    android:focusable="false" 
    android:focusableInTouchMode="false">

通过这种方式,它将像文本视图一样工作

于 2015-12-30T06:01:41.757 回答
1

首先,添加android:focusable="false"xml。在java代码中,只设置一个事件:

case R.id.edt_d_o_birth: {
            KeyboardUtils.hideSoftKeyboard(this);
            Calendar calendar = Calendar.getInstance(Locale.getDefault());
            DatePickerDialog datePickerDialog = new DatePickerDialog(RegisterActivity.this,
                    new DatePickerDialog.OnDateSetListener() {
                @Override
                public void onDateSet(DatePicker view, int year, int month, int dayOfMonth) {
                    //todo       
                }
            },calendar.get(Calendar.YEAR),calendar.get(Calendar.MONTH),calendar.get(Calendar.DAY_OF_MONTH));
            datePickerDialog.show();
            break;
        }
于 2017-04-10T09:04:26.607 回答
1

100% 工作代码

实施 implements View.OnClickListener

在 onCreate 里面 YourEditText.setOnClickListener(this);

@Override
    public void onClick(View v) {

        if (v == YourEditText) {

            // Get Current Date
            final Calendar c = Calendar.getInstance();
            mYear = c.get(Calendar.YEAR);
            mMonth = c.get(Calendar.MONTH);
            mDay = c.get(Calendar.DAY_OF_MONTH);


            DatePickerDialog datePickerDialog = new DatePickerDialog(this,
                    new DatePickerDialog.OnDateSetListener() {

                        @Override
                        public void onDateSet(DatePicker view, int year,
                                              int monthOfYear, int dayOfMonth) {

                            YourEditText.setText(dayOfMonth + "-" + (monthOfYear + 1) + "-" + year);

                        }
                    }, mYear, mMonth, mDay);
            datePickerDialog.show();
        }
}
于 2017-05-02T07:55:00.940 回答
1

将此添加到您的 EditText

 android:editable="false"
 android:focusable="false"
于 2017-10-10T08:35:56.070 回答
1

在 layout.xml 文件中,添加属性android:focusable=false,这肯定会工作

于 2019-03-08T12:18:46.330 回答
0

在 XML 文件中添加属性android:focusableInTouchMode="false"

 <EditText
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:focusableInTouchMode="false"
        android:hint="Some text"/>
于 2019-07-18T19:49:25.827 回答
0

试试这个

         <EditText
            android:id="@+id/et_mDate"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:clickable="false"
            android:cursorVisible="false"
            android:focusable="false"
            android:focusableInTouchMode="false"
            android:hint="Enter A Date in dd/mm/YYYY "
            android:inputType="date"
            android:padding="8dp" />
于 2020-02-05T06:26:24.717 回答
0

感谢 Lavekush Agrawal ,这对我有用,只需将其写在您的 onCreate 方法上

register_birthday.setInputType(InputType.TYPE_NULL);
register_birthday.requestFocus();
于 2020-05-01T15:16:59.373 回答
0

问题是您的编辑文本专注于第一次点击,而不是第二次点击它应用点击事件。所以你只需要设置焦点默认值,或者像我在 xml 中所做的那样添加一个属性,如下所示:

android:focusableInTouchMode="false"

在排序用下面替换你的xml,然后再试一次:

<EditText
        android:id="@+id/dateofBirth"
        android:layout_width="290dp"
        android:layout_height="wrap_content"
        android:layout_marginLeft="5dp"
        android:layout_marginTop="10dp"
        android:maxLines="1"
    android:focusableInTouchMode="false"
        android:hint="dd/mm/yyyy" />
于 2020-10-22T11:01:35.370 回答
0

如果要在编辑文本中单击打开对话框。请试试这个。

editTextNmae.setOnFocusChangeListener(new OnFocusChangeListener() {
@Override
public void onFocusChange(View v, boolean hasFocus) {
    if(hasFocus) {
       // call Date dialog box... 
    } else {
       // Hide Hide dialog box....
    }
}

});

于 2021-05-20T12:13:26.390 回答
0

当您使用 EditText 时,它会在您第一次单击它时获得焦点。只需在您的 xml 文件中添加可聚焦属性:

android:focusable="false"
于 2022-02-28T11:00:23.580 回答