• Android 自定义带回调的Dialog 及EditText相关


     
    import android.app.Activity;
    import android.content.Context;
    import android.text.Editable;
    import android.text.TextUtils;
    import android.text.TextWatcher;
    import android.view.LayoutInflater;
    import android.view.MotionEvent;
    import android.view.View;
    import android.view.View.OnClickListener;
    import android.view.View.OnTouchListener;
    import android.view.WindowManager;
    import android.view.inputmethod.InputMethodManager;
    import android.widget.Button;
    import android.widget.EditText;
    import android.widget.TextView;
    
    
    
    /**
     * 
     *         ModifyCountDialog ModifyCountDialog = new ModifyCountDialog.Builder(
     *                Activity.this,2030L).build();
     *         ModifyCountDialog.setModifyCountListener(new ModifyCountListener(){
     *            @Override
     *            public void onDelivered(long Count) {
     *                Log.d(TAG, "--------送你"+Count+"朵花");
     *            }
     *            
     *        });
     *        ModifyCountDialog.show();
     * 
     *
     */
    public class ModifyCountDialog extends popDialog implements OnClickListener
        ,OnTouchListener{
    
        private static final String TAG = "ModifyCountDialog";
        private static final int SCORE_PER_ = 10;    // currentScore = totalScore -  Count *  SCORE_PER_
    
        private Activity mActivity;
        private String title; // title string, have default
                                // R.string.dialog_deliver__title
        private long totalScore; // user total score
    
        private long mMaxCount = 0;
        private long mCurrentCount = 0;
        private long mCurrentScore;
    
        private Button mBtnCountSub;
        private Button mBtnCountAdd;
    
        private TextView mTvScore;
        private EditText mEditCount;
        
    //    private boolean isButtonCountChange=false;
    
        public static class Builder {
            private final Activity mActivity;
    
            private String title;
            private long score; // user current score
    
            /**
             * @param context
             * @param score
             */
            public Builder(Activity context, long score) {
                this.mActivity = context;
                this.score = score;
            }
    
            public Builder title(String title) {
                this.title = title;
                return this;
            }
    
            public ModifyCountDialog build() {
                return new ModifyCountDialog(this);
            }
        }
    
        private ModifyCountDialog(Builder builder) {
            super(builder.mActivity);
            this.mActivity = builder.mActivity;
            this.totalScore = builder.score;
    
            if (this.totalScore > 0) {
                this.mMaxCount = (long) (this.totalScore / SCORE_PER_);
                this.mCurrentScore = this.totalScore;
            }
    
            if (!TextUtils.isEmpty(builder.title)) {
                this.title = builder.title;
            }
    
            initDialog();
        }
    
        private void initDialog() {
            View view = LayoutInflater.from(mActivity).inflate(
                    R.layout.dialog_deliver_, null, false);
    
            
            view.findViewById(R.id.btn_cancle).setOnClickListener(this);
            view.findViewById(R.id.btn_deliver).setOnClickListener(this);
    
            mBtnCountSub = (Button) view
                    .findViewById(R.id.dialog_deliver__count_sub);
            mBtnCountSub.setOnClickListener(this);
    
            mBtnCountAdd = (Button) view
                    .findViewById(R.id.dialog_deliver__count_add);
            mBtnCountAdd.setOnClickListener(this);
    
            mTvScore = (TextView) view
                    .findViewById(R.id.dialog_deliver__score_tv);
            mTvScore.setText(String.valueOf(totalScore));
    
            mEditCount = (EditText) view
                    .findViewById(R.id.dialog_deliver__count);
    
            mEditCount.setOnTouchListener(this);
    
      //set keyboard property, the dialog will push up     getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE |WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN);
    
        this.build(view, true);
      }
    
      @Override
      public boolean onTouch(View v, MotionEvent event) {
        if(v.getId()==R.id.dialog_deliver_flower_count) {
          mEditFlowerCount.selectAll();    //select all character in EditText
          showKeyboard(mEditFlowerCount);    //without calling this. keyboard hide
          return true;
        }
        return false;
      }
    
    
    
    
      private boolean isCountLegal(long count){
            return (count >=0)&&(count <= mMaxCount);
        }
    
        /**
        * EditText text change watcher
        * 
        * when user input is illegal, setText to 0 or MaxCount
        * 
        * warn: call setText() in wrong place, will cause infinite loop and StackOverFlow
        * 
        */
        TextWatcher mTextWatcher = new TextWatcher() {
                private long mCount;
                 @Override
                public void onTextChanged(CharSequence s, int start, int before,int count) {
    
                }
    
                @Override
                public void beforeTextChanged(CharSequence s, int start, int count,int after) {
    
                }
    
                @Override
                public void afterTextChanged(Editable s) {
                        String str = s.toString();
                    //    Log.d(TAG, "---myc---afterTextChanged str------" + str);
                    if(!TextUtils.isEmpty(str) && TextUtils.isDigitsOnly(str)){
                           mCount = Long.parseLong(str);
                    }else{
                            mCount = 0;
                    }
    
                    //if user input is illegal, set to legal count
                    if(!isCountLegal(mCount)){
                            if(mCount < 0){
                                mCount = 0;
                             }else if(mCount > mMaxFlowerCount){
                                mCount = mMaxFlowerCount;
                            }
                            mEditFlowerCount.setText(String.valueOf(mCount));    //illegal, set to 0 or maxFlowerCount
                                 mEditFlowerCount.selectAll();    
                            }
                            setCurrentFlowerCount(mCount);
                            }
                       };
    
    
    
         /**
         * getter
         * 
         * @return
         */
        public long getCurrentCount() {
            return this.mCurrentCount;
        }
    
        /**
         * setter
         * 
         * @return
         */
        public void setCurrentCount(long Count) {
            if(isCountLegal(Count) && Count!=mCurrentCount){
                Log.d(TAG, "---setCurrentCount------" + Count);
                this.mCurrentCount = Count;
                refreshUI(Count);
            }
        }
        
        ModifyCountListener mModifyCountListener;
    
        public interface ModifyCountListener { //在Activity里弹框获取用户输入,可以通过回调的方法来获取用户输入值
            void onModified(long Count);
        }
    
        public void setModifyCountListener(ModifyCountListener listener) {
            mModifyCountListener = listener;
        }
    
        /**
         * user press "modify" button
         * 
         */
        private void doModifyCount() {
            if (mModifyCountListener != null) {
                mModifyCountListener.onModified(mCurrentCount);    //将值回调给Activity
            }
        }
    
        /**
         * refresh EditText, current core TextView and so on
         * 
         * @param Count
         */
        private void refreshUI(long Count) {
            mCurrentScore = totalScore - Count * SCORE_PER_;
    
            if (mCurrentScore >= 0) {
                mTvScore.setText(String.valueOf(mCurrentScore));
            }
    
            if (Count <= 0) {
                setBtnClickable(false, true);
            } else if (Count >= mMaxCount) {
                setBtnClickable(true, false);
            } else {
                setBtnClickable(true, true);
            }
        }
    
        /**
         * hide keyboard
         * 
         * @param v
         */
        private void hideKeyboard(View v) {
    //        Log.d(TAG, "---hideKeyboard()------");
            if(v == null){
                return;
            }
            InputMethodManager imm = (InputMethodManager) v.getContext()
                    .getSystemService(Context.INPUT_METHOD_SERVICE);
    
            imm.hideSoftInputFromWindow(v.getWindowToken(), 0);
        }
        
        
        /**
         * show keyboard
         * 
         * @param v
         */
        private void showKeyboard(View v) {
    //        Log.d(TAG, "---showKeyboard()------");
            if(v == null){
                return;
            }
            InputMethodManager imm = (InputMethodManager) v.getContext()
                    .getSystemService(Context.INPUT_METHOD_SERVICE);
    
            imm.showSoftInput(v, 0);
        }
        
        /**
         * set Button Clickable
         * 
         * @param canSub
         *            if true, can sub  count
         * @param canAdd
         *            if true, can add  count
         */
        private void setBtnClickable(boolean canSub, boolean canAdd) {
            mBtnCountSub.setClickable(canSub);
            mBtnCountAdd.setClickable(canAdd);
        }
    
    
    @Override
    public void onClick(View view) {
        if(!view.equals(R.id.dialog_deliver__count))      
        {
            hideKeyboard(mEditCount);
        }
       switch (view.getId()) {
            case R.id.btn_cancle:
                this.dismiss();
                break;
            case R.id.btn_deliver:
                doModifyCount();
                this.dismiss();
                break;
            case R.id.count_sub:
                if (mCurrentCount > 0) {
                    setCurrentCount(mCurrentCount - 1);
                    mEditCount.setText(String.valueOf(mCurrentCount));
                }
                break;
            case R.id.count_add:
                if (getCurrentCount() < mMaxCount) {
                    setCurrentCount(getCurrentCount() + 1);
                    mEditCount.setText(String.valueOf(mCurrentCount));
                }
                break;
            default:
                break;
            }
        }
    }                    

    包括

    (1)隐藏  和 弹出键盘

     1     /**
     2      * hide keyboard
     3      * 
     4      * @param v
     5      */
     6     private void hideKeyboard(View v) {
     7 //        Log.d(TAG, "---hideKeyboard()------");
     8         if(v == null){
     9             return;
    10         }
    11         InputMethodManager imm = (InputMethodManager) v.getContext()
    12                 .getSystemService(Context.INPUT_METHOD_SERVICE);
    13 
    14         imm.hideSoftInputFromWindow(v.getWindowToken(), 0);
    15     }
    16     
    17     
    18     /**
    19      * show keyboard
    20      * 
    21      * @param v
    22      */
    23     private void showKeyboard(View v) {
    24 //        Log.d(TAG, "---showKeyboard()------");
    25         if(v == null){
    26             return;
    27         }
    28         InputMethodManager imm = (InputMethodManager) v.getContext()
    29                 .getSystemService(Context.INPUT_METHOD_SERVICE);
    30 
    31         imm.showSoftInput(v, 0);
    32     }

    (2)防止键盘挡住输入框

    1         //set keyboard property, the dialog will push up  防止EditText被挡住, 往上推Dialog
    2         getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE |  
    3                 WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN);

    (3)点击EditText以外的区域,隐藏键盘,注意父view要设置onClickListener

    parentView.setOnClickListener(this); 
    

    @Override public void onClick(View view) { if(!view.equals(R.id.dialog_deliver__count))       { hideKeyboard(mEditCount); } }

    本来想在 EditText OnFocusListener()里监听, 失去焦点后,隐藏键盘. 不起作用

    因为对话框弹出的时候, EditText的isFocused是true的。除非点击按钮等,才会失去焦点。但是现在是想点击任何区域都失去焦点。

    所以需要通过监听整个父控件

    (4) 监听EditText输入     

    官方文档也指出:千万注意别在三个方法里随意重复调用setText,会死循环

    mEditCount.addTextChangedListener(mTextWatcher);        //先给EditText设置监听
     1    /**
     2      * EditText text change watcher                   
     3      * 
     4      * when user input is illegal, setText to 0 or MaxCount    
     5      * 
     6      * warn: call setText() in wrong place, will cause infinite loop and StackOverFlow  
     7      * 
     8      */
     9     TextWatcher mTextWatcher = new TextWatcher() {
    10         private long mCount;
    11         @Override
    12         public void onTextChanged(CharSequence s, int start, int before,
    13                 int count) {
    14             
    15         }
    16 
    17         @Override
    18         public void beforeTextChanged(CharSequence s, int start, int count,
    19                 int after) {
    20             
    21         }
    22 
    23         @Override
    24         public void afterTextChanged(Editable s) {
    25             String str = s.toString();
    26 //            Log.d(TAG, "---afterTextChanged str------" + str);
    27             
    28             if(!TextUtils.isEmpty(str) && TextUtils.isDigitsOnly(str)){
    29                 mCount = Long.parseLong(str);
    30             }else{
    31                 mCount = 0;
    32             }
    33             
    34             //if user input is illegal, set to legal count
    35             if(!isCountLegal(mCount)){
    36                 if(mCount < 0){
    37                     mCount = 0;
    38                 }else if(mCount > mMaxCount){
    39                     mCount = mMaxCount;
    40                 }
    41                 mEditCount.setText(String.valueOf(mCount));    //illegal, set to 0 or maxCount
    42                 mEditCount.selectAll();   //如果设置成最大值以后不全选,再点一个数字.s比最大值还大,EditText没反                                          //应,看起来就像失去焦点了. 但事实上调用 isFocused判断时, 还是有焦点的
    43             }
    44             setCurrentCount(mCount);
    45         }
    46     };

    (5)全选一个输入框的内容
    1     @Override
    2      public boolean onTouch(View v, MotionEvent event) {
    3         if(v.getId()==R.id.dialog_deliver__count) {
    4             mEditCount.selectAll();              //全选EditText的内容
    5             showKeyboard(mEditCount);            //全选完如果不调用这个,不弹出键盘
    6             return true;
    7         }
    8         return false;
    9     }
     
  • 相关阅读:
    RAID中条带的概念
    关于几个与IO相关的重要概念
    分布式调度
    ajax
    choices参数
    1.Python实现字符串反转的几种方法
    django web框架
    CRM总结
    Python面试重点(web篇)
    day02-网编并发数据库
  • 原文地址:https://www.cnblogs.com/maxiaodoubao/p/4729883.html
Copyright © 2020-2023  润新知