- 浏览: 737648 次
- 性别:
- 来自: 广州
-
文章分类
最新评论
-
lingsuch:
Android网络连接判断与处理 -
月光照着我:
写的不错,作为笔记了
Android中LayoutInflater的使用 -
智博王锋:
好文章是要顶的!
Android中LayoutInflater的使用 -
云南白药:
...
Android中LayoutInflater的使用 -
万新one:
理解了许多。解释的不错。3Q.
Android中LayoutInflater的使用
内容提要:
在手机这么小的屏幕上开发使用,难点之一就是频繁的屏幕切换。尽管midp2.0的UI部分已经很丰富了,但这些UI部件都是基于事件回调的。这在处理大量的、基本的问答式交互时显得力不从心。
本文实现了一个阻塞当前线程的对话框,简要地说,你可以运用诸如win32API中dialog函数那样的方式来实现对话框并阻塞等待返回值,然后根据返回值执行 不同的处理。听起来很诱人吧。
正文:
疑问何在?
首先回顾一下midp UI的事件处理机制。有两个要素:
1)首先UI部分由系统的一个线程负责维护。也就是说不能阻塞系统的事件处理要领。
2)事件处理运用的是一种回调机制。首先UI部件运用诸如setCommandListener之类的要领为自己注册一个回调接口(其中的回调要领由用户实现);等到触发了相应事件就调用这个注册好的接口的回调要领。
以下是一个实现了CommandListener的类的代码片断:
Form f=new Form("Hello world");
f.addCommand(exit);
f.setCommandListener(this);
可以想象基于事件回调的处理方式,在处理大量的、基本的问答式交互时显得力不从心。你不得不为每一个仅仅是询问要不要继续的对话框而实现一个又一个类,或者处理一个复杂的回调函数。如果选择后者,那么在一个又一个的if-else中处理不同逻辑事件的代码片断一定会烦死你。
较好的做法
这时候我们不免怀念一下win32 Api中对话框函数的处理方式:
int choose=Dialog(title,type……);
if(choose==OK){……}
else if(choose==Cancel){……}
这样处理将会阻塞当前线程,等待返回值,然后根据返回值执行 处理。这样做很cool的原由就是在一个逻辑性很完整的任务中,你可以一次性在一个回调要领中完成所有逻辑,而不必为了问询基本的YES/NO疑问而在不同的类中间跳来跳去。
如何在MIDP下实现
我们遇到的第一个疑问来自于我们的要领必须要阻塞当前线程等待返回值。也就是说,这个对话框不能在UI的回调中直接运行,比如commandAction中。处理办法是将所有的事件处理都放到一个线程类中处理。(这是一点额外的负担,但不可防止)。还好这个工作量不大,要想实现两个对象之间的通信也不难。
第二个疑问是如何 阻塞当前的线程,我们祭出Java线程的三板斧之wait()/notifyAll()。我们可以指定一个信号量(初值false),当其为false时阻塞当前线程,在得到用户通知后将信号量改为true,并唤醒线程。
演示源码:
package dialog; import javax.microedition.lcdui.Command; import javax.microedition.lcdui.CommandListener; import javax.microedition.lcdui.Display; import javax.microedition.lcdui.Displayable; import javax.microedition.lcdui.Form; import javax.microedition.midlet.MIDlet; import javax.microedition.midlet.MIDletStateChangeException; public class DialogTest extends MIDlet implements CommandListener { Display display; Form f = new Form("DialogTest"); Command showCMD = new Command("show", Command.ITEM, 1); public DialogTest() { super(); display = Display.getDisplay(this); f.addCommand(showCMD); f.setCommandListener(this); display.setCurrent(f); } protected void startApp() throws MIDletStateChangeException { } protected void pauseApp() { } protected void destroyApp(boolean arg0) throws MIDletStateChangeException { } public void commandAction(Command c, Displayable d) { new work1(c).start(); } class work1 extends Thread { Command c; public work1(Command c) { super(); this.c = c; } public void run() { // super.run(); if (c == showCMD) { int choose = new Dialog(display).show("Choose", "Do you like your Operation?", "yes", "no"); if (choose == Dialog.YES) { f.append("Yes,user like\n"); } else if (choose == Dialog.NO) { f.append("No,user like\n"); } display.setCurrent(f); } } } }
package dialog; import javax.microedition.lcdui.Command; import javax.microedition.lcdui.CommandListener; import javax.microedition.lcdui.Displayable; import javax.microedition.lcdui.Form; class DialogForm extends Form implements CommandListener {// UI部分 Command yesCMD; Command noCMD; Dialog dialog; public DialogForm(Dialog dialog, String title, String content, String yes, String no) { super(title); this.dialog = dialog; append(content); yesCMD = new Command(yes, Command.OK, 1); noCMD = new Command(no, Command.CANCEL, 1); addCommand(yesCMD); addCommand(noCMD); setCommandListener(this); } public void commandAction(Command c, Displayable d) { if (c == yesCMD) { dialog.setBlockFlag(true); dialog.setReturnValue(Dialog.YES); dialog.wakeup(); } else if (c == noCMD) { dialog.setBlockFlag(true); dialog.setReturnValue(Dialog.NO); dialog.wakeup(); } } }
package dialog; /* *为j2me提供阻塞的dialog调用要领。 *但前提是,如果要在UI的相应线程中运行(比如commonAction), *则需首先打开一个新的线程中运用,因为UI线程是不可以阻塞的。 *这个版本虽然包含在coreUI2.0中,但midp1.0也可以用。seimens s57通过测试。 * */ import javax.microedition.lcdui.Display; import javax.microedition.lcdui.Form; /** * @author Favo */ public class Dialog {// 主类 private boolean blockFlag = false; public static int YES = 0; public static int NO = 1; private int returnValue; private Display display; public Dialog(Display display) { this.display = display; } public void setReturnValue(int i) {// 配置返回值 returnValue = i; } synchronized boolean getBlockFlag() {// 取得信号量 return blockFlag; } synchronized void setBlockFlag(boolean flag) {// 配置信号量 blockFlag = flag; } public int show(String title, String content, String yes, String no) { setBlockFlag(false); Form f = new DialogForm(this, title, content, yes, no); display.setCurrent(f);// 显示UI try { while (getBlockFlag() == false) {// 如果用户没选择阻塞 synchronized (this) { wait(); } } } catch (InterruptedException e) { e.printStackTrace(); System.out.println("InterruptedException in Dialog.show"); } return returnValue;// 返回 } public void wakeup() { synchronized (this) {// 唤醒阻塞的线程 notifyAll(); } } }
发表评论
-
J2ME 第三方开源库(UI扩展等.)
2012-07-02 00:31 1040J2ME自带UI不是太美观,使用起来也不太 ... -
解决J2me项目使用第三方jar包引发的问题.
2012-02-12 21:53 2042使用了第三方包引发的问题: 1.配置模拟器时报Set Pla ... -
J2me-WMA编程(无线消息接口)
2010-07-02 14:04 16411 WMA编程 1.1 WMA概述:(wireless M ... -
J2me点阵字
2010-07-02 14:02 1444前言:开发J2ME过程中,我们会发现平台本身提供的字体太小,而 ... -
各种优化J2me的开源库
2010-03-01 21:22 1196J2ME自带UI不是太美观,使用起来也不太 ... -
J2me Property属性表
2010-01-14 19:19 1003在J2ME开发中,我们经常需要和手机系统进行交互,获得一些和系 ... -
PNG数据分析
2010-01-14 18:20 2545png图片的压缩与解压缩 ... -
FileConnection访问本地文件系统
2010-01-14 17:46 2085FC api是JSR 75, PDA Optional Pac ... -
RMS笔记
2010-01-14 17:02 1237RMS(Record Management System)是M ... -
J2me FileConnection
2010-01-14 17:00 2207J2me文件系统 几个问题 1,可选包的概念 什么是J2 ... -
J2me实现半透明效果
2009-10-30 19:44 2385在J2ME MIDP1.0规范中并未实现半透明 功能,只有少数 ... -
J2ME读取各种格式的文本文件
2009-10-30 19:09 2467在J2ME中读取各种格式的文本文件 在J2ME开发过程中 ... -
由jar文件生成jad文件
2009-10-20 14:18 2860首先说明的是JAD文件是干嘛用的。用数据线上传游戏或电子书时, ... -
J2me的27种字体效果(不包括下划线)(附图)
2009-09-01 01:05 2216import javax.microedition.lcdui ... -
Eclipse单步调试j2me程序
2009-08-27 18:59 3608使用Eclipse调试J2ME程序 Eclipse ... -
安装SonyEricsson_J2ME_SDK
2009-07-04 09:40 1200最近研究J2ME,在搭建开发平台后运行程序时出现了一些问题,开 ... -
eclipse及中文包下载地址
2009-07-01 14:16 3655eclipse及中文包下载地址 eclipse最新版官方下 ... -
J2me getProperty(String key)之五字段含义.
2009-06-30 21:23 1328import javax.microedition.lcdui ... -
destroyApp()参数说明
2009-06-10 21:16 1632destroyApp是一个callback,它是一个接口或者说 ... -
Could not find jar tool executable
2009-05-27 15:10 2088Could not find jar tool executa ...
相关推荐
5. **创建J2ME项目**:在MyEclipse中,选择"File" -> "New" -> "Other",在弹出的对话框中,展开"EclipseME",选择"J2ME Project",点击"Next",输入项目名,选择相应的设备配置,如CLDC/MIDP,然后"Finish"。...
2. **新建J2ME项目**:在Eclipse中,选择"File" > "New" > "Other",然后在弹出的对话框中找到并选择J2ME相关的项目模板,如"J2ME Application"或"J2ME MIDlet Suite",点击"Next",按照向导提示设置项目名称和配置...
以创建一个简单的“Hello World”项目为例,打开KToolBar并点击New Project按钮,在弹出的对话框中输入项目名称为“HelloWorld”和MIDlet类名为“Hello”。创建项目后,系统会自动生成项目框架,并提示将编写好的...
余志龙,来自于手机制造业、电视媒体业、网络、电信产业、软件开发等领域,擅长嵌入式系统软件设计、J2ME游戏开发、Android开发,以及J2EE、JSP、Servlet、JavaBeans、PHP、C#等程序语言,熟悉面向对象技术与Eclipse...