仿造LWUIT textField的一次尝试
2009-11-20 20:10
92 查看
在应用程序开发中经常遇到用户输入的问题;Sun MIDP提供了TextField控件;这个控件用起来不方便,一个原因是TextField的实现,不同的java虚拟机移植,实现不同,有的java虚拟机实现不方便,应用开发者对此无能为力;比如我现在用的这个j2me平台,用户输入必须要先暂停虚拟机,切换到另一个本地实现的窗口,输入完毕后,再恢复虚拟机;客户对此抱怨很大;另一个原因是高级UI入门简单,但要实现自己想要的功能,就显得不灵活,而且经常会添乱。所以,我决定写一个用户输入类,支持英文字符输入和数字输入,支持输入模式切换,不支持汉字输入,不需要暂停虚拟机。而LWUIT的TextField控件恰好实现了我想要的功能。
简单地模仿它写了一段测试代码:
基本的原理是:
1. keyPress和keyRepeated;通过特殊的按键切换输入模式、删除键值;我这里没有做光标;
2. 一种输入模式对应一个Hashtable,然后将所有的输入模式放在一个hashtable;根据输入模式、键值和按键次数查询字符;
实际的效果并不好;经过测试发现,当一直按住某个键时,首先是keyPressed被回调,然后是keyRepeated不断地被调用;要切换某个字符,唯一的选择是一直按住某个键,直到想要的那个字符出现;而实际的情况是,按键的响应快过显示结果,很难精确地在看到某个字符时释放按键。
还需要改进。
简单地模仿它写了一段测试代码:
import javax.microedition.lcdui.Graphics; import javax.microedition.lcdui.*; import java.util.Hashtable; import java.util.Vector; public class inputCanvas extends Canvas{ String m_strInput = ""; private static Hashtable inputModes; private static Vector v_InputMode = new Vector(); private static Object s_CurrInputMode; private static final String[] DEFAULT_KEY_CODES = { // 0 " 0", // 1 ".,?!'/"1-()@/:_", // 2 "ABC2", // 3 "DEF3", // 4 "GHI4", // 5 "JKL5", // 6 "MNO6", // 7 "PQRS7", // 8 "TUV8", // 9 "WXYZ9", }; private int m_iPressCount = 0; private int m_iPrevKeyCode = 0; private final static int fs_maxLength = 10; static{ initInputModes(); } public inputCanvas(){ this.setFullScreenMode(true); } public void paint(Graphics g){ g.setColor(0xFFFFFF); g.fillRect(0, 0, this.getWidth(), this.getHeight()); g.setColor(0x000000); g.drawString(m_strInput, 0, 0, Graphics.LEFT|Graphics.TOP); g.drawString((String)s_CurrInputMode, 0, 50, Graphics.LEFT|Graphics.TOP); } protected void keyPressed(int keyCode){ m_iPressCount = 0; m_iPrevKeyCode = keyCode; if((keyCode >= 48)&&(keyCode <= 57)){ char c = getCharPerKeyCode(m_iPressCount,(keyCode-48)); insertChars(""+c,false); }else if(keyCode == 35){ switchInputModes(); }else if(keyCode == -7){ deleteChar(); } repaint(); } protected void keyRepeated(int keyCode){ if((keyCode >= 48)&&(keyCode <= 57)&&(m_iPrevKeyCode == keyCode)){ m_iPressCount++; char c = getCharPerKeyCode(m_iPressCount,(keyCode-48)); insertChars(""+c,true); repaint(); } } protected void deleteChar(){ if(m_strInput.length() > 0){ m_strInput = m_strInput.substring(0, m_strInput.length()-1); } } protected void insertChars(String c, boolean bOverWrite){ if(c == null){ return; } if(c.length() != 1){ return; } if(bOverWrite){ m_strInput = m_strInput.substring(0, m_strInput.length()-1)+c; }else{ if(m_strInput.length() < fs_maxLength){ m_strInput = m_strInput + c; } } } protected char getCharPerKeyCode(int pressCount, int keyCode){ Hashtable mode = (Hashtable)inputModes.get(s_CurrInputMode); String str = (String)mode.get(new Integer(keyCode+'0')); if(str != null){ pressCount = pressCount%str.length(); return str.charAt(pressCount); } return 0; } private void switchInputModes(){ int iIndex = v_InputMode.indexOf(s_CurrInputMode); iIndex = (iIndex+1)%v_InputMode.size(); s_CurrInputMode = v_InputMode.elementAt(iIndex); } private static void initInputModes(){ if(inputModes == null) { inputModes = new Hashtable(); Hashtable upcase = new Hashtable(); for(int iter = 0 ; iter < DEFAULT_KEY_CODES.length ; iter++) { upcase.put(new Integer('0' + iter), DEFAULT_KEY_CODES[iter]); } v_InputMode.addElement("ABC"); inputModes.put("ABC", upcase); Hashtable lowcase = new Hashtable(); for(int iter = 0 ; iter < DEFAULT_KEY_CODES.length ; iter++) { lowcase.put(new Integer('0' + iter), DEFAULT_KEY_CODES[iter].toLowerCase()); } v_InputMode.addElement("abc"); inputModes.put("abc", lowcase); Hashtable numbers = new Hashtable(); for(int iter = 0 ; iter < 10 ; iter++) { numbers.put(new Integer('0' + iter), "" + iter); } inputModes.put("123", numbers); v_InputMode.addElement("123"); s_CurrInputMode = v_InputMode.elementAt(0); } } }
基本的原理是:
1. keyPress和keyRepeated;通过特殊的按键切换输入模式、删除键值;我这里没有做光标;
2. 一种输入模式对应一个Hashtable,然后将所有的输入模式放在一个hashtable;根据输入模式、键值和按键次数查询字符;
实际的效果并不好;经过测试发现,当一直按住某个键时,首先是keyPressed被回调,然后是keyRepeated不断地被调用;要切换某个字符,唯一的选择是一直按住某个键,直到想要的那个字符出现;而实际的情况是,按键的响应快过显示结果,很难精确地在看到某个字符时释放按键。
还需要改进。
相关文章推荐
- 解决Transport Security has blocked a cleartext HTTP resource load since it is insecure
- Cocoa NSTableView, NSTextFieldCell, NSCell, ImageAndTextCell tutorial
- extjs form textfield的隐藏方法
- 自定义ScrollEditText,解决ScrollView中嵌套EditText的问题
- QML行编辑器TextField
- cocos2dx 3.x 解决输入框(TextField,TextFieldTTF) 输入中文变乱码的问题
- DropDownlist的DataTextField显示多列数据
- TextField关键字
- iOS开发之textField限制输入字数
- Unity3D 设置Label TextField字体字号大小
- iOS TextField属性大全
- 如何让textField输入框 限制输入字数的同时,还只让输入数字和字母
- iOS模拟器,点击textfield为什么不弹出软键盘
- Flash的输入框TextField无法输入中文的问题
- textField 限制2位小数,编辑时不让键盘挡住
- Js前台彩票系统,全JS前台制作,属于个人学习js以来的一次尝试
- This tag and its children can be replaced by one <TextView/> and a compound drawable
- 一次域渗透尝试
- sublime:a plugin may be making sublime text unresponsuve by taking too long in its o
- App Transport Security has blocked a cleartext HTTP (http://) resource load since it is insecure. Te