Android custom input method soft keyboard

1 Function description

  • There is a text edit box in the main interface of the touch screen device, and a numeric keyboard is fixed at the bottom area. In addition to the number keys, the keyboard also has the functions of * and # keys;
  • Provide a custom digital input method, generate the apk installation package file, and embed it in the img image file.

2 Design and implementation

  1. Create a class named SimpleIME, inherit the parent class InputMethodService, and implement the KeyboardView.OnKeyboardActionListener interface.
  2. Write the .xml file loaded by the keyboard object.
  3. Override the onCreateInputView() method, initialize the keyboard view and create the keyboard object, and use the keyboard view object to set the keyboard monitor.
  4. Rewrite the onKey, onPress, onRelease, onText, swipeDown, swipeLeft, swipeRight, and swipeUp methods. The keyboard operation can be handled in the onKey method. In this method, the corresponding operation is performed through the incoming primaryCode. There is no specific implementation of other methods.
  5. The declaration service of the configuration manifest file also applied to the system for the BIND_INPUT_METHOD permission of the IME, and added a filter named android.view.InputMethod to the IME to store the attributes of the intent.

3 Post the code

  1. SimpleIME.java
import android.inputmethodservice.InputMethodService;
import android.inputmethodservice.Keyboard;
import android.inputmethodservice.KeyboardView;
import android.media.AudioManager;
import android.view.KeyEvent;
import android.view.View;
import android.view.inputmethod.InputConnection;

/**
 * @description: 自定义输入法
 * @version: v1.0
 * @author: yeyl
 * @date: 2018/6/26 14:57
 * @history:
 */
public class SimpleIME extends InputMethodService
        implements KeyboardView.OnKeyboardActionListener {
    
    

    private KeyboardView mKeyboardView;
    private Keyboard mKeyboard;
    /**
     * 大小写转换的flag
     */
    private boolean mCaps = false;

    @Override
    public View onCreateInputView() {
    
    
        mKeyboardView = (KeyboardView) getLayoutInflater().inflate(R.layout.layout_keyboard, null);
        mKeyboard = new Keyboard(this, R.xml.keyboard_number);
        mKeyboardView.setKeyboard(mKeyboard);
        mKeyboardView.setOnKeyboardActionListener(this);
        return mKeyboardView;
    }

    @Override
    public boolean onKeyDown(int keyCode, KeyEvent event) {
    
    
        return super.onKeyDown(keyCode, event);
    }

    @Override
    public void onKey(int primaryCode, int[] keyCodes) {
    
    
        InputConnection ic = getCurrentInputConnection();
        playClick(primaryCode);
        switch (primaryCode) {
    
    
            case Keyboard.KEYCODE_DELETE:
                // 回退
                ic.deleteSurroundingText(1, 0);
                break;
            case Keyboard.KEYCODE_SHIFT:
                // 大小写切换
                mCaps = !mCaps;
                mKeyboard.setShifted(mCaps);
                mKeyboardView.invalidateAllKeys();
                break;
            case Keyboard.KEYCODE_DONE:
                // 完成
                ic.sendKeyEvent(new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_ENTER));
                break;
            case Keyboard.KEYCODE_CANCEL:
                // 取消
                ic.sendKeyEvent(new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_BACK));
                ic.sendKeyEvent(new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_BACK));
                break;
            default:
                char code = (char) primaryCode;
                if (Character.isLetter(code) && mCaps) {
    
    
                    code = Character.toUpperCase(code);
                }
                ic.commitText(String.valueOf(code), 1);
        }
    }

    /**
     * 播放按键音
     *
     * @param keyCode 键码
     */
    private void playClick(int keyCode) {
    
    
        AudioManager am = (AudioManager) getSystemService(AUDIO_SERVICE);
        switch (keyCode) {
    
    
            case 32:
                am.playSoundEffect(AudioManager.FX_KEYPRESS_SPACEBAR);
                break;
            case Keyboard.KEYCODE_DONE:
            case 10:
                am.playSoundEffect(AudioManager.FX_KEYPRESS_RETURN);
                break;
            case Keyboard.KEYCODE_DELETE:
                am.playSoundEffect(AudioManager.FX_KEYPRESS_DELETE);
                break;
            default:
                am.playSoundEffect(AudioManager.FX_KEYPRESS_STANDARD);
        }
    }

    @Override
    public void onPress(int primaryCode) {
    
    
    }

    @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() {
    
    
    }
}
  1. layout_keyboard.xml
<?xml version="1.0" encoding="UTF-8"?>
<android.inputmethodservice.KeyboardView xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/keyboard"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_alignParentBottom="true"
    android:keyPreviewLayout="@layout/layout_preview" />
  1. layout_preview.xml
<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="#FFFF00"
    android:gravity="center"
    android:textSize="30sp"
    android:textStyle="bold" />
  1. keyboard_number.xml
<?xml version="1.0" encoding="utf-8"?>
<Keyboard xmlns:android="http://schemas.android.com/apk/res/android"
    android:horizontalGap="0px"
    android:keyWidth="33.3%p"
    android:keyHeight="9%p"
    android:verticalGap="0px">
    <Row>
        <Key
            android:codes="49"
            android:keyEdgeFlags="left"
            android:keyLabel="1" />
        <Key
            android:codes="50"
            android:keyLabel="2" />
        <Key
            android:codes="51"
            android:keyEdgeFlags="right"
            android:keyLabel="3" />
    </Row>
    <Row>
        <Key
            android:codes="52"
            android:keyEdgeFlags="left"
            android:keyLabel="4" />
        <Key
            android:codes="53"
            android:keyLabel="5" />
        <Key
            android:codes="54"
            android:keyEdgeFlags="right"
            android:keyLabel="6" />
    </Row>
    <Row>
        <Key
            android:codes="55"
            android:keyEdgeFlags="left"
            android:keyLabel="7" />
        <Key
            android:codes="56"
            android:keyLabel="8" />
        <Key
            android:codes="57"
            android:keyEdgeFlags="right"
            android:keyLabel="9" />
    </Row>
    <Row android:rowEdgeFlags="bottom">
        <Key
            android:codes="-3"
            android:keyEdgeFlags="left"
            android:keyLabel="*" />
        <Key
            android:codes="48"
            android:keyLabel="0" />
        <Key
            android:codes="-4"
            android:isRepeatable="true"
            android:keyEdgeFlags="right"
            android:keyLabel="完成" />
    </Row>
</Keyboard>
  1. AndroidManifest.xml
        <service
            android:name=".SimpleIME"
            android:label="@string/simple_ime"
            android:permission="android.permission.BIND_INPUT_METHOD">
            <meta-data
                android:name="android.view.im"
                android:resource="@xml/method" />
            <intent-filter>
                <action android:name="android.view.InputMethod" />
            </intent-filter>
        </service>
  1. method.xml
<?xml version="1.0" encoding="utf-8"?>
<input-method xmlns:android="http://schemas.android.com/apk/res/android">
    <subtype
        android:imeSubtypeLocale="en_US"
        android:imeSubtypeMode="keyboard"
        android:label="@string/subtype_en_US" />
</input-method>

4 Demo screenshot

Demo screenshot

Guess you like

Origin blog.csdn.net/discode/article/details/115048712