使用警报对话框摇动动画(如果无效信息摇动编辑文本并且不解除)

时间:2011-04-07 07:43:48

标签: android android-layout

所以我有一个用户输入数据的对话框,这是用户的年龄。所以我希望当/如果用户将编辑文本留空时,edittext将像api演示中那样进行摇动动画。到目前为止,当输入无效信息时,我无法通过不解除对话。感谢。

mInflater = (LayoutInflater) Information.this.getSystemService(LAYOUT_INFLATER_SERVICE);
        mLayout = mInflater.inflate(R.layout.agedialog, null);

        mAgeEditText = (EditText) mLayout.findViewById(R.id.AgeEditText);
        mAgeResultTextView = (TextView) findViewById(R.id.AgeResultTextView);
        final Animation shake = AnimationUtils.loadAnimation(Information.this, R.anim.shake);

        mInputManager = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
        mInputManager.toggleSoftInput(InputMethodManager.SHOW_FORCED, InputMethodManager.HIDE_IMPLICIT_ONLY);

        new AlertDialog.Builder(Information.this).setView(mLayout).setTitle(R.string.EnterYourAge)
                .setPositiveButton(R.string.OK, new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int id) {
                        mInputManager.hideSoftInputFromWindow(mAgeEditText.getWindowToken(), 0);
                        if (TextUtils.isEmpty(mAgeEditText.getText())) {
                            mAgeEditText.startAnimation(shake);
                            // here the dialog dismisses even if I call startAnimation
                        }
                        else {
                            HelperClass.getInstance().setAge(Integer.parseInt(mAgeEditText.getText().toString()));
                            mAgeResultTextView.setText(HelperClass.getInstance().getAge());
                        }
                    }
                }).setNegativeButton(R.string.Cancel, new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int id) {
                        mInputManager.hideSoftInputFromWindow(mAgeEditText.getWindowToken(), 0);
                        dialog.cancel();
                    }
                }).show();

4 个答案:

答案 0 :(得分:4)

好的,所以在我被问到这个问题后很长一段时间我都找到了答案但是如果有人想要这个,我认为继续发布答案是明智的。

基本上这不能通过警报对话框完成,它与单击按钮和负按钮时的行为有关。但是,可以使用常规Dialog来完成。你需要一些动画xmls,这些可以在res下的api demo的anim文件夹中找到(原始java文件是api演示中的Animation1.java,所以你可以检查出来)。我也做了这样,键盘准备好供用户输入。你可以通过删除所有输入管理器的东西来摆脱它。无论如何这里是对话框的代码。

public void showAgeDialog() {
    final Dialog dialog = new Dialog(Information.this);

    dialog.setContentView(R.layout.age_dialog);
    dialog.setTitle(R.string.InputAge);

    final EditText ageEditText = (EditText) dialog.findViewById(R.id.AgeEditText);

    inputManager.toggleSoftInput(InputMethodManager.SHOW_FORCED, InputMethodManager.HIDE_IMPLICIT_ONLY);

    dialog.show();

    Button positive = (Button) dialog.findViewById(R.id.OkButton);
    Button negative = (Button) dialog.findViewById(R.id.CancelButton);

    positive.setOnClickListener(new Button.OnClickListener() {
        public void onClick(View v) {
            if (ageEditText.getText().toString().isEmpty()) {
                Animation shake = AnimationUtils.loadAnimation(Information.this, R.anim.shake);
                ageEditText.startAnimation(shake);
                Toast.makeText(Information.this, "Please enter an age", Toast.LENGTH_SHORT).show();
            }
            else {
                database.updateAge(Integer.parseInt(ageEditText.getText().toString()));
                inputManager.hideSoftInputFromWindow(ageEditText.getWindowToken(), 0);
                dialog.dismiss();
            }
        }
    });

    negative.setOnClickListener(new Button.OnClickListener() {
        public void onClick(View v) {
            inputManager.hideSoftInputFromWindow(ageEditText.getWindowToken(), 0);
            dialog.dismiss();
        }
    });
}

这是我布局的代码。我使这个对话框看起来就像一个警告对话框,带有确认和取消按钮以及灰色背景。

    <?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:orientation="vertical" >

    <EditText
        android:id="@+id/AgeEditText"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_gravity="center"
        android:layout_marginBottom="18dp"
        android:layout_marginLeft="100dp"
        android:layout_marginRight="100dp"
        android:hint="@string/Years"
        android:inputType="number"
        android:maxLength="2"
        android:textSize="18sp" >
    </EditText>

    <LinearLayout
        style="@android:style/ButtonBar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal" >

        <Button
            android:id="@+id/OkButton"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:text="@string/Ok" />

        <Button
            android:id="@+id/CancelButton"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:text="@string/Cancel" />
    </LinearLayout>

</LinearLayout>

答案 1 :(得分:3)

一个额外的夏日爱情故事:

如果您想晃动整个AlertDialog ,则不仅可以EditText,还可以在对话框片段中执行以下操作:

(注意!为了清楚起见,我省略了任何健全性检查,例如示例代码中对上下文和窗口的null验证)

public Dialog onCreateDialog(Bundle savedInstanceState) {

    // Create the alert dialog as usual.
    AlertDialog shakyAlertDialog = new AlertDialog.Builder(getContext())
            .setTitle(R.string.title)
            .setMessage(R.string.message)    // Optional
            .setView(R.layout.input)         // This one holds your EditText
            .setNegativeButton(R.string.cancel, null)
            .setPositiveButton(R.string.ok, null)
            .show();

    // Get hold of the edit text we want to validate on.
    EditText input = shakyAlertDialog.findViewById(R.id.age_input);

    // Replace the "OK" button's click listener. As discussed in previous
    // answers this will replace the auto-dismiss behavior.
    shakyAlertDialog
            .getButton(DialogInterface.BUTTON_POSITIVE)
            .setOnClickListener(view -> {
                if (input.getText().isEmpty()) {
                    // This is the gold. This is how we shake the entire
                    // AlertDialog, not only the EditText.
                    shakyAlertDialog
                            .getWindow()
                            .getDecorView()
                            .animate()
                            .translationX(16f)
                            .setInterpolator(new CycleInterpolator(7f))
                } else {
                    // Do something with the input, but don't
                    // forget to manually dismiss the dialog.
                    shakyAlertDialog.dismiss()
                }
            });

    return shakyAlertDialog;
}

答案 2 :(得分:0)

请参阅我的回答Android: Dialog dismisses without calling dismiss,不要删除对话框。

答案 3 :(得分:0)

使用AlertDialog实现OP请求是绝对可能的。但是,有必要进行一些调整。

AlertDialog会在您使用构建器创建的按钮上注册自己的OnClickListener。在解除对话之前,这些处理程序将委托给您的注册听众。

规避此默认行为的解决方案是在调用show()后立即注册自己的处理程序,从而覆盖对话框自己的侦听器:

mLayout = mInflater.inflate(R.layout.agedialog, null);
mAgeEditText = (EditText) mLayout.findViewById(R.id.AgeEditText);
mAgeResultTextView = (TextView) findViewById(R.id.AgeResultTextView);

Animation shake = AnimationUtils.loadAnimation(Information.this, R.anim.shake);

// create dialog with buttons but without registering click listeners
AlertDialog dialog = new AlertDialog.Builder(Information.this)
    .setView(mLayout)
    .setTitle(R.string.EnterYourAge)
    .setPositiveButton(R.string.OK, null) // only declare button, add listener later
    .setNegativeButton(R.string.Cancel, null) // dito
    .create();

// define click listeners for ok and cancel
OnClickListener okListener = new OnClickListener() {
    public void onClick(View button) {
        mInputManager.hideSoftInputFromWindow(mAgeEditText.getWindowToken(), 0);
        if (TextUtils.isEmpty(mAgeEditText.getText())) {
            // input not valid -> shake
            mAgeEditText.startAnimation(shake);
        }
        else {
            HelperClass.getInstance().setAge(Integer.parseInt(mAgeEditText.getText().toString()));
            mAgeResultTextView.setText(HelperClass.getInstance().getAge());
            dialog.dismiss(); // close dialog, since input is valid
        }
    }
};
OnClickListener cancelListener = ...

// show dialog and immediately register our own listeners afterwards
dialog.show();
dialog.getButton(AlertDialog.BUTTON_POSITIVE).setOnClickListener(okListener);
dialog.getButton(AlertDialog.BUTTON_NEGATIVE).setOnClickListener(cancelListener);