在android中创建自定义键盘

时间:2015-06-14 13:52:41

标签: android android-softkeyboard android-keypad android-input-method

我想在我的Android应用中创建一个自定义键盘,如下所示:

https://www.dropbox.com/s/vwiz4o3pd8q4o81/2015-06-14%2014.53.02.jpg?dl=0

我曾尝试使用键盘视图但无法获得我想要的内容。我也在线查看了自定义键盘上的教程,但似乎没有提示如何制作我想要的键盘。我已经尝试将png图像作为键盘的背景,但这没有帮助。到目前为止,我已经做到了这一点:

https://www.dropbox.com/s/xrm4v941ofecmut/2015-06-14%2014.54.10.jpg?dl=0

我是否可以获得有助于解决问题的教程和代码的帮助或链接。

这是我目前的代码:

<?xml version="1.0" encoding="utf-8"?>
<Keyboard xmlns:android="http://schemas.android.com/apk/res/android"
    android:keyWidth="14.25%p"
    android:hapticFeedbackEnabled="true"
    android:keyHeight="8.5%p">
<!--
    android:horizontalGap="0.50%p"
    android:verticalGap="0.50%p"
    NOTE When we add a horizontalGap in pixels, this interferes with keyWidth in percentages adding up to 100%
    NOTE When we have a horizontalGap (on Keyboard level) of 0, this make the horizontalGap (on Key level) to move from after the key to before the key... (I consider this a bug) 
 -->
    <Row>
            <Key android:codes="-1"     android:keyLabel="EVALUATE" android:keyWidth="42.75%p"  android:keyEdgeFlags="left"   />
            <Key android:codes="-100"     android:keyLabel="RESET" android:keyWidth="28.50%p"     />
            <Key android:codes="-1000"     android:keyLabel="\u24D8" android:keyWidth="28.50%p"    android:keyEdgeFlags="right"  />
    </Row> 

    <Row>
        <Key android:codes="1"      android:keyLabel="sin"     android:keyEdgeFlags="left" />
        <Key android:codes="2"      android:keyLabel="cos"  />
        <Key android:codes="3"      android:keyLabel="tan"  />
        <Key android:codes="36"     android:keyLabel="sinh"        />
        <Key android:codes="37"     android:keyLabel="cosh"     />
        <Key android:codes="38"     android:keyLabel="tanh"   />
        <Key android:codes="-2"     android:keyIcon="@drawable/delete_symbol"        android:isRepeatable="true"     android:keyEdgeFlags="right"/>
    </Row>   

    <Row>
        <Key android:codes="4"      android:keyLabel="asin"      android:keyEdgeFlags="left" />
        <Key android:codes="5"      android:keyLabel="acos"    />
        <Key android:codes="6"      android:keyLabel="atan"  />
        <Key android:codes="42"     android:keyLabel="asinh"        />
        <Key android:codes="43"     android:keyLabel="acosh"     />
        <Key android:codes="44"     android:keyLabel="atanh"   />
        <Key android:codes="21"     android:keyLabel="\u00F7"   android:keyEdgeFlags="right" />   
    </Row>
    <Row>
        <Key android:codes="7"      android:keyLabel="cosec"       android:keyEdgeFlags="left" />
        <Key android:codes="8"      android:keyLabel="sec"      />
        <Key android:codes="9"      android:keyLabel="cot"      />
        <Key android:codes="33"     android:keyLabel="7"        />
        <Key android:codes="34"     android:keyLabel="8"       />
        <Key android:codes="35"     android:keyLabel="9"      />
        <Key android:codes="20"     android:keyLabel="\u00D7"    android:keyEdgeFlags="right" />   
    </Row>
    <Row>
        <Key android:codes="11"     android:keyLabel="e^("    />
        <Key android:codes="12"     android:keyLabel="ln("   />
        <Key android:codes="22"     android:keyLabel="x\u207F" />
        <Key android:codes="30"     android:keyLabel="4"       />
        <Key android:codes="31"     android:keyLabel="5"        />
        <Key android:codes="32"     android:keyLabel="6"     />
        <Key android:codes="19"     android:keyLabel="\u2212"   android:keyEdgeFlags="right" />
    </Row>
    <Row>
        <Key android:codes="14"     android:keyLabel="k"        android:keyEdgeFlags="left" />
        <Key android:codes="15"     android:keyLabel="\u03C0"  />
        <Key android:codes="13"     android:keyIcon="@drawable/italic_x"  />
        <Key android:codes="27"     android:keyLabel="1"         />
        <Key android:codes="28"     android:keyLabel="2"        />
        <Key android:codes="29"     android:keyLabel="3"      />
        <Key android:codes="18"     android:keyLabel="+"     android:keyEdgeFlags="right" />
    </Row>
    <Row>
        <Key android:codes="-3"     android:keyIcon="@drawable/keyboard_done"  android:keyWidth="28.5%p" android:keyEdgeFlags="left"   />   
        <Key android:codes="10"     android:keyLabel="\u221a"  />
        <Key android:codes="16"     android:keyLabel="("         />
        <Key android:codes="26"     android:keyLabel="0"      />
        <Key android:codes="17"     android:keyLabel=")"   />  
        <Key android:codes="23"     android:keyLabel="." android:keyEdgeFlags="right" />
    </Row>

</Keyboard>

包含xml文件的java处理程序的代码是:

class CustomKeyboard {

private Activity  mHostActivity;

private Button doneButton = null;
private Button clearButton = null;
private Button infoButton = null;

/** The key (code) handler. */
private OnKeyboardActionListener mOnKeyboardActionListener = new OnKeyboardActionListener() {

public final static int CodeEvaluate  = -1;
public final static int CodeClear  = -100;
public final static int CodeInfo  = -1000;
public final static int CodeDelete    = -2; // Keyboard.KEYCODE_DELETE
public final static int CodeHide      = -3; // Keyboard.KEYCODE_CANCEL

public final static int CodeMINIMUM   = 0;
public final static int CodeSin       = 1;
public final static int CodeCos       = 2;
public final static int CodeTan       = 3;
public final static int CodeAsin      = 4;
public final static int CodeAcos      = 5;
public final static int CodeAtan      = 6;
public final static int CodeCosec     = 7;
public final static int CodeSec       = 8;
public final static int CodeCot       = 9;
public final static int CodeSqrt      = 10;
public final static int CodeExp       = 11;
public final static int CodeLn        = 12;
public final static int CodeX         = 13;
public final static int CodeK         = 14;
public final static int CodePI        = 15;
public final static int CodeOpenB     = 16;
public final static int CodeCloseB    = 17;
public final static int CodePlus      = 18;
public final static int CodeMinus     = 19;
public final static int CodeMultiply  = 20;
public final static int CodeDivide    = 21;
public final static int CodePower     = 22;
public final static int CodePoint     = 23;
public final static int CodeABC       = 24;
public final static int CodeSpace     = 25;

public final static int CodeMAXIMUM   = 50;   // maximum number of Keys

public String[] keyCodeToText = null;

public void keysInitialise()
{
if(keyCodeToText==null) keyCodeToText = new String[CodeMAXIMUM];
keyCodeToText[CodeSin]      = "sin(";
keyCodeToText[CodeCos]      = "cos(";
keyCodeToText[CodeTan]      = "tan(";
keyCodeToText[CodeAsin]     = "asin(";
keyCodeToText[CodeAcos]     = "acos(";
keyCodeToText[CodeAtan]     = "atan(";
keyCodeToText[CodeCosec]    = "cosec(";
keyCodeToText[CodeSec]      = "sec(";
keyCodeToText[CodeCot]      = "cot(";
keyCodeToText[CodeSqrt]     = "sqrt(";
keyCodeToText[CodeExp]      = "e^(";
keyCodeToText[CodeLn]       = "ln(";
keyCodeToText[CodeX]        = "x";
keyCodeToText[CodeK]        = "k";
keyCodeToText[CodePI]       = "pi";
keyCodeToText[CodeOpenB]    = "(";
keyCodeToText[CodeCloseB]   = ")";
keyCodeToText[CodePlus]     = "+";
keyCodeToText[CodeMinus]    = "-";
keyCodeToText[CodeMultiply] = "*";
keyCodeToText[CodeDivide]   = "/";
keyCodeToText[CodePower]    = "^";
keyCodeToText[CodePoint]    = ".";
keyCodeToText[CodeABC  ]    = "";
}


@Override 
public void onKey(int primaryCode, int[] keyCodes) {

// Get the EditText and its Editable
View focusCurrent = mHostActivity.getWindow().getCurrentFocus();
if( focusCurrent==null || focusCurrent.getClass()!=EditText.class )    return;

EditText edittext = (EditText) focusCurrent;
Editable editable = edittext.getText();
int start = edittext.getSelectionStart();

keysInitialise();

// Apply the key to the edittext
if(primaryCode == CodeEvaluate) {
if(doneButton != null) doneButton.performClick();
}
else if (primaryCode == CodeClear){
if(clearButton != null) clearButton.performClick();
}
else if (primaryCode == CodeInfo){
if(infoButton != null) infoButton.performClick();
}
else if(primaryCode ==CodeDelete) {
if( editable!=null && start>0 ) editable.delete(start - 1, start);
}
else if(primaryCode == CodeHide) {
hideCustomKeyboard();
}
else if(primaryCode > CodeMINIMUM && primaryCode < CodeMAXIMUM) {
editable.insert(start, keyCodeToText[primaryCode]);
}
else editable.insert(start, Integer.toString(primaryCode));
}

@Override public void onPress(int arg0) {
}

@Override public void onRelease(int primaryCode) {
}

@Override public void onText(CharSequence text) {
}

public CustomKeyboard(Activity host, int viewid, int layoutid) {
mHostActivity= host;
mKeyboardView= (KeyboardView)mHostActivity.findViewById(viewid);
mKeyboardView.setKeyboard(new Keyboard(mHostActivity, layoutid));
mKeyboardView.setPreviewEnabled(false); // NOTE Do not show the preview balloons
mKeyboardView.setOnKeyboardActionListener(mOnKeyboardActionListener);
}

/** Returns whether the CustomKeyboard is visible. */
public boolean isCustomKeyboardVisible() {
    return mKeyboardView.getVisibility() == View.VISIBLE;
}

/** Make the CustomKeyboard visible, and hide the system keyboard for the given view. */
public void showCustomKeyboard(View v) {
mKeyboardView.setVisibility(View.VISIBLE);
mKeyboardView.setEnabled(true);
}

/** Make the CustomKeyboard invisible. */
public void hideCustomKeyboard() {
mKeyboardView.setVisibility(View.GONE);
mKeyboardView.setEnabled(false);
}

/** Hide standard keyboard */
private void hideStandardKeyboard(View v) {
    if(v != null) ((InputMethodManager)mHostActivity.getSystemService(Activity.INPUT_METHOD_SERVICE)).hideSoftInputFromWindow(v.getWindowToken(), 0);
}

/** Register the doneButton for which doneButton.performClick()
 *  will be called when the "Done" keypad-button is clicked.
 */
public void registerDoneButton (Button doneButton) {
this.doneButton = doneButton;
}
public void registerClearButton (Button clearButton) {
this.clearButton = clearButton;
}
public void registerInfoButton (Button infoButton) {
this.infoButton = infoButton;
}
/**
* Register <var>EditText<var> for using this custom keyboard.
*
* @param The EditText that registers to the custom keyboard.
*/
public void registerEditText(EditText edittext) {

// Make the custom keyboard appear or disappear
edittext.setOnFocusChangeListener(new OnFocusChangeListener() {
@Override public void onFocusChange(View v, boolean hasFocus) {
if(hasFocus) showCustomKeyboard(v);
else hideCustomKeyboard();
}
});

edittext.setOnClickListener(new OnClickListener() {
@Override public void onClick(View v) {
showCustomKeyboard(v);
}
});

edittext.setOnTouchListener(new OnTouchListener() {
@Override public boolean onTouch(View v, MotionEvent event) {
((EditText) v).onTouchEvent(event);
hideStandardKeyboard(v);
return true; // Consume touch event
}
});
}

1 个答案:

答案 0 :(得分:1)

由于您具有键盘的布局xml,因此使键盘等于第一张图像中显示的键盘。您应该具有关键视图的背景并将其添加到每个键。