欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

Android编程实现自定义输入法功能示例【输入密码时防止第三方窃取】

程序员文章站 2024-02-20 12:17:04
本文实例讲述了android编程实现自定义输入法功能。分享给大家供大家参考,具体如下: 对于android用户而言,一般都会使用第三方的输入法。可是,在输入密码时(尤其是...

本文实例讲述了android编程实现自定义输入法功能。分享给大家供大家参考,具体如下:

对于android用户而言,一般都会使用第三方的输入法。可是,在输入密码时(尤其是支付相关的密码),使用第三方输入法有极大的安全隐患。目前很多网银类的app和支付宝等软件在用户输入密码时,都会弹出自定义的输入法而不是直接使用系统输入法。

这里介绍的就是如何实现一个简单的自定义输入法。当然,也可以自己写一个dialog加上几十个按钮让用户输入,只不过这样显得不够专业。

(一)首先上效果图:

1.前面两个输入框使用了自定义的输入法:

Android编程实现自定义输入法功能示例【输入密码时防止第三方窃取】

2.第三个输入框没有进行任何设置,因此将使用默认的输入法:

Android编程实现自定义输入法功能示例【输入密码时防止第三方窃取】

(二)代码简介:

1.主页面布局,由3个输入框加上一个android.inputmethodservice.keyboardview组成。android.inputmethodservice.keyboardview是一个系统自带的继承自view的组件,但是它不在android.view这个包下面,因此这里需要写上完整的包名。

<relativelayout xmlns:android="http://schemas.android.com/apk/res/android"
  android:layout_width="match_parent"
  android:layout_height="match_parent">
  <!--前两个edittext均使用自定义的输入法-->
  <edittext
    android:id="@+id/input_password"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_margin="8dp"
    android:hint="one password"
    android:layout_alignparenttop="true"
    android:inputtype="textpassword" />
  <edittext
    android:id="@+id/input_password2"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_below="@+id/input_password"
    android:layout_margin="8dp"
    android:hint="another password"
    android:inputtype="textpassword" />
  <!--这个edittext使用默认的输入法-->
  <edittext
    android:id="@+id/input_normal_text"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_below="@+id/input_password2"
    android:layout_margin="8dp"
    android:hint="normal text" />
  <android.inputmethodservice.keyboardview
    android:id="@+id/keyboardview"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_alignparentbottom="true"
    android:layout_centerhorizontal="true"
    android:focusable="true"
    android:focusableintouchmode="true"
    android:visibility="gone" />
</relativelayout>

2.keyboardview是一个显示输入法的容器控件,使用时需要设置具体的输入法面板内容。

(1)首先在res下新建xml目录,然后创建文件keys_layout.xml,即输入法面板的内容。每个row表示一行,keyboad的属性keywidth和keyheight表示每个按键的大小,25%p表示占父组件的25%. key的属性codes表示该按键的编号(点击时系统回调方法中会返回这个值,用以区分不同的按键),keylabel表示按键上面显示的文字。还有很多其它的属性,不再陈述。

<?xml version="1.0" encoding="utf-8"?>
<keyboard xmlns:android="http://schemas.android.com/apk/res/android"
  android:keywidth="25%p"
  android:keyheight="10%p">
  <row>
    <key
      android:codes="55"
      android:keylabel="7"
      android:keyedgeflags="left" />
    <key
      android:codes="56"
      android:keylabel="8" />
    <key
      android:codes="57"
      android:keylabel="9" />
    <!--删除按键长按时连续响应-->
    <key
      android:codes="60001"
      android:keylabel="del"
      android:isrepeatable="true" />
  </row>
  <row>
    <key
      android:codes="52"
      android:keylabel="4"
      android:keyedgeflags="left" />
    <key
      android:codes="53"
      android:keylabel="5" />
    <key
      android:codes="54"
      android:keylabel="6" />
    <key
      android:codes="48"
      android:keylabel="0" />
  </row>
  <row>
    <key
      android:codes="49"
      android:keylabel="1"
      android:keyedgeflags="left" />
    <key
      android:codes="50"
      android:keylabel="2" />
    <key
      android:codes="51"
      android:keylabel="3" />
    <key
      android:codes="60002"
      android:keylabel="cancel" />
  </row>
</keyboard>

(2)为了使用方便,新建一个类:keyboardbuilder.java,用于初始化自定义输入法和绑定edittext,代码如下:

public class keyboardbuilder {
  private static final string tag = "keyboardbuilder";
  private activity mactivity;
  private keyboardview mkeyboardview;
  public keyboardbuilder(activity ac, keyboardview keyboardview, int keyboardxmlresid) {
    mactivity = ac;
    mkeyboardview = keyboardview;
    keyboard mkeyboard = new keyboard(mactivity, keyboardxmlresid);
    // attach the keyboard to the view
    mkeyboardview.setkeyboard(mkeyboard);
    // do not show the preview balloons
    mkeyboardview.setpreviewenabled(false);
    keyboardview.onkeyboardactionlistener keyboardlistener = new keyboardview.onkeyboardactionlistener() {
      @override
      public void onkey(int primarycode, int[] keycodes) {
        // get the edittext and its editable
        view focuscurrent = mactivity.getwindow().getcurrentfocus();
        if (focuscurrent == null || !(focuscurrent instanceof edittext)) {
          return;
        }
        edittext edittext = (edittext) focuscurrent;
        editable editable = edittext.gettext();
        int start = edittext.getselectionstart();
        // handle key
        if (primarycode == constant.codecancel) {
          hidecustomkeyboard();
        } else if (primarycode == constant.codedelete) {
          if (editable != null && start > 0) {
            editable.delete(start - 1, start);
          }
        } else {
          // insert character
          editable.insert(start, character.tostring((char) primarycode));
        }
      }
      @override
      public void onpress(int arg0) {
      }
      @override
      public void onrelease(int primarycode) {
      }
      @override
      public void ontext(charsequence text) {
      }
      @override
      public void swipedown() {
      }
      @override
      public void swipeleft() {
      }
      @override
      public void swiperight() {
      }
      @override
      public void swipeup() {
      }
    };
    mkeyboardview.setonkeyboardactionlistener(keyboardlistener);
  }
  //绑定一个edittext
  public void registeredittext(edittext edittext) {
    // make the custom keyboard appear
    edittext.setonfocuschangelistener(new view.onfocuschangelistener() {
      @override
      public void onfocuschange(view v, boolean hasfocus) {
        if (hasfocus) {
          showcustomkeyboard(v);
        } else {
          hidecustomkeyboard();
        }
      }
    });
    edittext.setonclicklistener(new view.onclicklistener() {
      @override
      public void onclick(view v) {
        log.d(tag, "onclick");
        showcustomkeyboard(v);
      }
    });
    edittext.setontouchlistener(new view.ontouchlistener() {
      @override
      public boolean ontouch(view v, motionevent event) {
        log.d(tag, "ontouch");
        edittext edittext = (edittext) v;
        int intype = edittext.getinputtype();    // backup the input type
        edittext.setinputtype(inputtype.type_null); // disable standard keyboard
        edittext.ontouchevent(event);        // call native handler
        edittext.setinputtype(intype);       // restore input type
        edittext.setselection(edittext.gettext().length());
        return true;
      }
    });
  }
  public void hidecustomkeyboard() {
    mkeyboardview.setvisibility(view.gone);
    mkeyboardview.setenabled(false);
  }
  public void showcustomkeyboard(view v) {
    mkeyboardview.setvisibility(view.visible);
    mkeyboardview.setenabled(true);
    if (v != null) {
      ((inputmethodmanager) mactivity.getsystemservice(activity.input_method_service)).hidesoftinputfromwindow(v.getwindowtoken(), 0);
    }
  }
  public boolean iscustomkeyboardvisible() {
    return mkeyboardview.getvisibility() == view.visible;
  }
}

3.最后是主activity的代码,这里就很简单了。

/**
 * 自定义安全输入法
 */
public class mainactivity extends actionbaractivity {
  private keyboardbuilder builder;
  @override
  protected void oncreate(bundle savedinstancestate) {
    super.oncreate(savedinstancestate);
    setcontentview(r.layout.activity_main);
    getwindow().setsoftinputmode(windowmanager.layoutparams.soft_input_state_always_hidden);
    keyboardview keyboardview = (keyboardview) findviewbyid(r.id.keyboardview);
    builder = new keyboardbuilder(this, keyboardview, r.xml.keys_layout);
    edittext edittext = (edittext) findviewbyid(r.id.input_password);
    builder.registeredittext(edittext);
    edittext edittext2 = (edittext) findviewbyid(r.id.input_password2);
    builder.registeredittext(edittext2);
  }
  @override
  public void onbackpressed() {
    if (builder != null && builder.iscustomkeyboardvisible()) {
      builder.hidecustomkeyboard();
    } else {
      this.finish();
    }
  }
}

更多关于android相关内容感兴趣的读者可查看本站专题:《android视图view技巧总结》、《android开发动画技巧汇总》、《android编程之activity操作技巧总结》、《android布局layout技巧总结》、《android开发入门与进阶教程》、《android资源操作技巧汇总》及《android控件用法总结

希望本文所述对大家android程序设计有所帮助。