仿映客直播的键盘弹出效果

来源:互联网 发布:sql develop下载 编辑:程序博客网 时间:2024/05/21 22:59

   很久没写博客了,因为最近有些茫然,好了不废话,说主题,做IM模块的同学应该都知道有一个UI效果一般是跑不掉的,就是发送消息到公屏上

   我现在要在这里展示的就是模仿映客做的一个键盘弹出,发送消息的效果.,先上一张图,不然看不到效果大伙也没兴趣往下看了.


   开始的时候觉得很简单,设置下windowSoftInputMode,写一个EditText,然后点击之后弹出来,点击空白区域消失吗,在一系列的demo之后发觉真的不是那么简单,各种方法试过,什么 ViewTreeObserver,onSizeChanged(),要么就是得不到键盘高度,要么就是视图被压缩了,总之就是都失败了

苦试无果之后,各种百度,google,可惜没有找到一个满意的demo,看了别人说可以用浮层来做,就想到了popupwindow,又一番实验之后发觉不可行,最好决定再试试dialog,然后,嘿,可以了,达到了满意的效果,好了说这么多废话,上代码了,

自定义dialog:

package org.dync.softkeyboarddemo;import android.app.Dialog;import android.content.Context;import android.graphics.PorterDuff;import android.graphics.Rect;import android.text.InputType;import android.text.TextUtils;import android.util.Log;import android.view.KeyEvent;import android.view.View;import android.view.inputmethod.InputMethodManager;import android.widget.Button;import android.widget.EditText;import android.widget.LinearLayout;import android.widget.RelativeLayout;import android.widget.TextView;import android.widget.Toast;import java.lang.reflect.Field;/** * 文本输入框 */public class InputTextDialog extends Dialog {    public interface OnTextSendListener {        void onTextSend(String msg, boolean tanmuOpen);    }    private TextView confirmBtn;    private LinearLayout mBarrageArea;    private EditText messageTextView;    private static final String TAG = InputTextDialog.class.getSimpleName();    private Context mContext;    private InputMethodManager imm;    private RelativeLayout rlDlg;    private int mLastDiff = 0;    private LinearLayout mConfirmArea;    private OnTextSendListener mOnTextSendListener;    private boolean mDanmuOpen = false;//    private final String reg = "[`~@#$%^&*()-_+=|{}':;,/.<>¥…()—【】‘;:”“’。,、]";//    private Pattern pattern = Pattern.compile(reg);    public InputTextDialog(Context context, int theme) {        super(context, theme);        mContext = context;        setContentView(R.layout.dialog_input_text);        messageTextView = (EditText) findViewById(R.id.et_input_message);        messageTextView.setInputType(InputType.TYPE_CLASS_TEXT);        //修改下划线颜色        messageTextView.getBackground().setColorFilter(context.getResources().getColor(R.color.transparent), PorterDuff.Mode.CLEAR);        try {            //修改光光标颜色            Field ft = TextView.class.getDeclaredField("mCursorDrawableRes");            ft.setAccessible(true);            ft.set(messageTextView, R.drawable.edit_select);        } catch (Exception e) {            e.printStackTrace();        }        confirmBtn = (TextView) findViewById(R.id.confrim_btn);        imm = (InputMethodManager) mContext.getSystemService(Context.INPUT_METHOD_SERVICE);        confirmBtn.setOnClickListener(new View.OnClickListener() {            @Override            public void onClick(View view) {                String msg = messageTextView.getText().toString().trim();                if (!TextUtils.isEmpty(msg)) {                    mOnTextSendListener.onTextSend(msg, mDanmuOpen);                    imm.showSoftInput(messageTextView, InputMethodManager.SHOW_FORCED);                    imm.hideSoftInputFromWindow(messageTextView.getWindowToken(), 0);                    messageTextView.setText("");                    dismiss();                } else {                    Toast.makeText(mContext, "input can not be empty!", Toast.LENGTH_LONG).show();                }                messageTextView.setText(null);            }        });        final Button barrageBtn = (Button) findViewById(R.id.barrage_btn);        barrageBtn.setOnClickListener(new View.OnClickListener() {            @Override            public void onClick(View view) {                mDanmuOpen = !mDanmuOpen;                if (mDanmuOpen) {                    barrageBtn.setBackgroundResource(R.drawable.barrage_slider_on);                } else {                    barrageBtn.setBackgroundResource(R.drawable.barrage_slider_off);                }            }        });        mBarrageArea = (LinearLayout) findViewById(R.id.barrage_area);        mBarrageArea.setOnClickListener(new View.OnClickListener() {            @Override            public void onClick(View v) {                mDanmuOpen = !mDanmuOpen;                if (mDanmuOpen) {                    barrageBtn.setBackgroundResource(R.drawable.barrage_slider_on);                } else {                    barrageBtn.setBackgroundResource(R.drawable.barrage_slider_off);                }            }        });        //监听键盘        messageTextView.setOnEditorActionListener(new TextView.OnEditorActionListener() {            @Override            public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {                switch (actionId) {                    case KeyEvent.KEYCODE_ENDCALL:                    case KeyEvent.KEYCODE_ENTER:                        if (messageTextView.getText().length() > 0) {//                            mOnTextSendListener.onTextSend("" + messageTextView.getText(), mDanmuOpen);                            //sendText("" + messageTextView.getText());                            //imm.showSoftInput(messageTextView, InputMethodManager.SHOW_FORCED);                            imm.hideSoftInputFromWindow(messageTextView.getWindowToken(), 0);//                            messageTextView.setText("");                            dismiss();                        } else {                            Toast.makeText(mContext, "input can not be empty!", Toast.LENGTH_LONG).show();                        }                        return true;                    case KeyEvent.KEYCODE_BACK:                        dismiss();                        return false;                    default:                        return false;                }            }        });        mConfirmArea = (LinearLayout) findViewById(R.id.confirm_area);        mConfirmArea.setOnClickListener(new View.OnClickListener() {            @Override            public void onClick(View v) {                String msg = messageTextView.getText().toString().trim();                if (!TextUtils.isEmpty(msg)) {                    mOnTextSendListener.onTextSend(msg, mDanmuOpen);                    imm.showSoftInput(messageTextView, InputMethodManager.SHOW_FORCED);                    imm.hideSoftInputFromWindow(messageTextView.getWindowToken(), 0);                    messageTextView.setText("");                    dismiss();                } else {                    Toast.makeText(mContext, "input can not be empty!", Toast.LENGTH_LONG).show();                }                messageTextView.setText(null);            }        });        messageTextView.setOnKeyListener(new View.OnKeyListener() {            @Override            public boolean onKey(View view, int i, KeyEvent keyEvent) {                Log.d("My test", "onKey " + keyEvent.getCharacters());                return false;            }        });        rlDlg = (RelativeLayout) findViewById(R.id.rl_outside_view);        rlDlg.setOnClickListener(new View.OnClickListener() {            @Override            public void onClick(View v) {                //点击编辑区域以上的位置,dialog消失                if (v.getId() != R.id.rl_inputdlg_view)                    dismiss();            }        });        final LinearLayout rldlgview = (LinearLayout) findViewById(R.id.rl_inputdlg_view);        //dialog消失键盘会消失,但是键盘消失,dialog不一定消失,比如按软键盘上的消失键,键盘消失,dialog不会消失        // 所以在这里监听键盘的高度,如果高度为0则表示键盘消失,那么就应该dimiss dialog        rldlgview.addOnLayoutChangeListener(new View.OnLayoutChangeListener() {            @Override            public void onLayoutChange(View view, int i, int i1, int i2, int i3, int i4, int i5, int i6, int i7) {                Rect r = new Rect();                //获取当前界面可视部分                getWindow().getDecorView().getWindowVisibleDisplayFrame(r);                //获取屏幕的高度                int screenHeight = getWindow().getDecorView().getRootView().getHeight();                //此处就是用来获取键盘的高度的, 在键盘没有弹出的时候 此高度为0 键盘弹出的时候为一个正数                int heightDifference = screenHeight - r.bottom;                if (heightDifference <= 0 && mLastDiff > 0) {                    //imm.hideSoftInputFromWindow(messageTextView.getWindowToken(), 0);                    dismiss();                }                mLastDiff = heightDifference;            }        });        //点击编辑外部layout键盘消失,这个可有可无//        rldlgview.setOnClickListener(new View.OnClickListener() {//            @Override//            public void onClick(View v) {//                imm.hideSoftInputFromWindow(messageTextView.getWindowToken(), 0);//                dismiss();//            }//        });    }    public void setmOnTextSendListener(OnTextSendListener onTextSendListener) {        this.mOnTextSendListener = onTextSendListener;    }    @Override    public void dismiss() {        super.dismiss();        //dismiss之前重置mLastDiff值避免下次无法打开        mLastDiff = 0;    }    @Override    public void show() {        super.show();    }}

直接看这个代码可能有点不太懂,其实原理就是利用dialog的dimiss,因为EditText纯在与dialog中,dialog消失之后,EditText也会消失,那么键盘自然就消失了,注释也写的很详细了,有基础的同学肯定可以看懂的,后面也会把demo地址发出来

dialog_input_text.xml:

<?xml version="1.0" encoding="utf-8"?><RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:id="@+id/rl_outside_view"    android:layout_width="match_parent"    android:layout_height="wrap_content"    android:orientation="horizontal">    <LinearLayout        android:id="@+id/rl_inputdlg_view"        android:layout_width="match_parent"        android:layout_height="wrap_content"        android:background="@color/color_input_dialog_background"        android:orientation="horizontal"        android:layout_alignParentBottom="true">        <LinearLayout            android:id="@+id/barrage_area"            android:orientation="horizontal"            android:layout_weight="0.3"            android:layout_gravity="center_vertical"            android:layout_width="wrap_content"            android:layout_height="wrap_content">            <Button                android:id="@+id/barrage_btn"                android:layout_width="40dp"                android:layout_marginLeft="10dp"                android:layout_height="25dp"                android:layout_marginRight="10dp"                android:background="@drawable/barrage_slider_off" />        </LinearLayout>        <View android:layout_width="0.5dp"            android:layout_height="match_parent"            android:layout_marginTop="10dp"            android:layout_marginBottom="10dp"            android:layout_marginLeft="6dp"            android:layout_marginStart="6dp"            android:background="@color/colorTransparentBlack"/>        <EditText            android:id="@+id/et_input_message"            android:hint="@string/dialog_input_text_hint"            android:layout_width="match_parent"            android:layout_weight="4"            android:layout_height="wrap_content"            android:imeActionId="@+id/login"            android:imeOptions="actionUnspecified"            android:inputType="text"            android:maxLength="32"            android:textColor="@color/black"            android:maxLines="1"            android:singleLine="true" />        <View android:layout_width="0.5dp"            android:layout_height="match_parent"            android:layout_marginTop="10dp"            android:layout_marginBottom="10dp"            android:layout_marginLeft="6dp"            android:layout_marginStart="6dp"            android:background="@color/colorTransparentBlack"/>        <LinearLayout            android:id="@+id/confirm_area"            android:layout_width="wrap_content"            android:layout_gravity="center"            android:layout_height="wrap_content">            <Button                android:id="@+id/confrim_btn"                android:layout_width="50dp"                android:layout_height="30dp"                android:background="@drawable/btn_send_message"                android:gravity="center"                android:textColor="@color/colorAccent"                android:text="发送" />        </LinearLayout>    </LinearLayout></RelativeLayout>

 

这个是输入消息的dialog,嗯,没什么可说的,后面的也不发了,小demo,资源文件也有一些,太久没写博客了,自定义空间方面的东西也没啥好说的,还是直接上地址,大家去copy了看效果吧.

地址:百度网盘


0 0
原创粉丝点击