我这天,开发网络连接程序,遇到n多问题,都得以解决。
总结一下。
首先是环境。
我用的开发SDK和模拟器都是Sun的,J2ME Wireless Toolkit 2.2
现在UltraEdit下面写一个网络程序。注意一定要在网络连接动作时,另外启动一下线程,否则模拟器运行会有错误。
很不好的代码:不要使用!!!!!!!!!!
import java.io.InputStream;
import java.io.OutputStream;
import javax.microedition.io.Connector;
import javax.microedition.io.HttpConnection;
import javax.microedition.io.StreamConnection;
import javax.microedition.lcdui.Alert;
import javax.microedition.lcdui.AlertType;
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.lcdui.TextBox;
import javax.microedition.lcdui.TextField;
import javax.microedition.midlet.MIDlet;
import javax.microedition.midlet.MIDletStateChangeException;
public class MainMidlet extends MIDlet
implements CommandListener
{
private Display display;
public MainMidlet() {
super();
display = Display.getDisplay(this);
}
private Form f;
private TextField server;
private TextField port;
private TextBox showBox;
protected void startApp() throws MIDletStateChangeException {
f = new Form("Test Network");
server = new TextField("服务器","www.google.com",20,TextField.ANY);
port = new TextField("端口","80",4,TextField.NUMERIC);
showBox = new TextBox("连接数据", "Init",1024,TextField.ANY);
showBox.addCommand(new Command("返回",Command.BACK,1));
showBox.setCommandListener(this);
f.append(server);
f.append(port);
f.addCommand(new Command("Socket连接",Command.SCREEN,1));
f.addCommand(new Command("Http连接",Command.SCREEN,1));
f.setCommandListener(this);
display.setCurrent(f);
}
protected void pauseApp() {
// TODO Auto-generated method stub
}
protected void destroyApp(boolean arg0) throws MIDletStateChangeException {
// TODO Auto-generated method stub
}
public void commandAction(Command arg0, Displayable arg1) {
if(arg0.getLabel().equals("Socket连接"))
{
socketconnect();
}
else if(arg0.getLabel().equals("Http连接"))
{
httpconnect();
}
else if(arg0.getLabel().equals("返回"))
{
display.setCurrent(f);
}
}
private void socketconnect()
{
StreamConnection socket = null;
InputStream is = null;
OutputStream os = null;
try{
String name = "http://" + server.getString() + ":" + port.getString();
socket = (StreamConnection)Connector.open(name,Connector.READ_WRITE);
String request = "GET / HTTP/1.0\n\n";
os = socket.openOutputStream();
os.write(request.getBytes());
is = socket.openInputStream();
final int MAX_LENGTH = 128;
byte[] buf = new byte[MAX_LENGTH];
int total = 0;
while(total < MAX_LENGTH){
int count = is.read(buf,total, MAX_LENGTH - total);
if(count < 0)
{
break;
}
total += count;
}
String toshow = new String(buf,0,buf.length);
showBox.setString(toshow);
display.setCurrent(showBox);
}catch(Exception ex)
{
Alert al = new Alert("未定义异常", ex.getMessage(), null, AlertType.ALARM);
al.setTimeout(Alert.FOREVER);
display.setCurrent(al,f);
}finally{
if(is != null)
{
try{
is.close();
}catch(Exception ex)
{
Alert al = new Alert("未定义异常", ex.getMessage(), null, AlertType.ALARM);
al.setTimeout(Alert.FOREVER);
display.setCurrent(al,f);
}
is = null;
}
if(os != null)
{
try{
os.close();
}catch(Exception ex)
{
Alert al = new Alert("未定义异常", ex.getMessage(), null, AlertType.ALARM);
al.setTimeout(Alert.FOREVER);
display.setCurrent(al,f);
}
os = null;
}
if(socket != null)
{
try{
socket.close();
}catch(Exception ex)
{
Alert al = new Alert("未定义异常", ex.getMessage(), null, AlertType.ALARM);
al.setTimeout(Alert.FOREVER);
display.setCurrent(al,f);
}
socket = null;
}
}
}
private void httpconnect()
{
HttpConnection conn = null;
InputStream is = null;
OutputStream os = null;
try{
String url = "wap.winwap.com";
conn = (HttpConnection)Connector.open("http://10.0.0.172/" + "home.wml");
conn.setRequestProperty("X-Online-Host",url);
conn.setRequestMethod(HttpConnection.GET);
if(conn.getResponseCode() == HttpConnection.HTTP_OK)
{
is = conn.openInputStream();
final int MAX_LENTH = 128;
byte[] buf = new byte[MAX_LENTH];
int total = 0;
while(total < MAX_LENTH)
{
int count = is.read(buf,total,MAX_LENTH - total);
if(count < 0)
break;
total += count;
}
is.close();
String reply = new String(buf,0,total);
showBox.setString(reply);
display.setCurrent(showBox);
}else{
showBox.insert(String.valueOf(conn.getResponseCode()),showBox.getCaretPosition());
showBox.insert(String.valueOf(HttpConnection.HTTP_OK),showBox.getCaretPosition());
display.setCurrent(showBox);
}
}catch(Exception ex)
{
Alert al = new Alert("未定义异常", ex.getMessage(), null, AlertType.ALARM);
al.setTimeout(Alert.FOREVER);
display.setCurrent(al,showBox);
}finally{
if(is != null)
{
try{
is.close();
}catch(Exception ex)
{
Alert al = new Alert("未定义异常", ex.getMessage(), null, AlertType.ALARM);
al.setTimeout(Alert.FOREVER);
display.setCurrent(al,showBox);
}
is = null;
}
if(os != null)
{
try{
os.close();
}catch(Exception ex)
{
Alert al = new Alert("未定义异常", ex.getMessage(), null, AlertType.ALARM);
al.setTimeout(Alert.FOREVER);
display.setCurrent(al,showBox);
}
os = null;
}
if(conn != null)
{
try{
conn.close();
}catch(Exception ex)
{
Alert al = new Alert("未定义异常", ex.getMessage(), null, AlertType.ALARM);
al.setTimeout(Alert.FOREVER);
display.setCurrent(al,showBox);
}
conn = null;
}
}
}
}
这段代码,在模拟器上运行很有问题!
这以后,再按钮就没有反应了,而且,会有警告warning
警告: 若要避免潜在的死锁,应该在 commandAction() 处理程序之外的其他线程中执行
可能会阻塞的
操作(如网络连接)。
模拟器再不能正常链接了。无法配置。
===============================================
改代码如下:
import javax.microedition.io.*;
import java.io.*;
import javax.microedition.midlet.*;
import javax.microedition.lcdui.*;
public class QueryForm extends TextBox implements CommandListener
{
MIDlet midlet ;
public QueryForm(MIDlet m)
{
super("请输入网址","http://wap.winwap.com",40,TextField.ANY) ;
midlet = m ;
addCommand(new Command("离开",Command.SCREEN,1)) ;
addCommand(new Command("查询",Command.SCREEN,1)) ;
setCommandListener(this) ;
}
public void commandAction(Command c,Displayable s)
{
String cmd = c.getLabel() ;
if(cmd.equals("离开"))
{
midlet.notifyDestroyed() ;
}else if(cmd.equals("查询"))
{
String url = getString() ; //连接网址
WorkThread wt = new WorkThread(url,Display.getDisplay(midlet)) ;
wt.start() ;
}
}
}
import javax.microedition.io.*;
import java.io.*;
import javax.microedition.midlet.*;
import javax.microedition.lcdui.*;
public class MyHttpClient extends MIDlet
{
Display display ;
public MyHttpClient()
{
display = Display.getDisplay(this) ;
}
public void startApp()
{
display.setCurrent(new QueryForm(this));
}
public void pauseApp()
{
}
public void destroyApp(boolean con)
{
}
}
import javax.microedition.io.*;
import java.io.*;
import javax.microedition.midlet.*;
import javax.microedition.lcdui.*;
public class WorkThread extends Thread
{
String url ;
Display display ;
public WorkThread(String url,Display d)
{
this.url = url ;
display = d ;
System.out.println("准备连接:"+this.url) ;
}
public void run()
{
HttpConnection conn = null;
InputStream is = null;
InputStreamReader isr = null ;
StringBuffer line = new StringBuffer("");
try {
conn = (HttpConnection)Connector.open(url);
System.out.println("内容长度:" + conn.getLength()) ;
is = conn.openInputStream();
isr = new InputStreamReader(is) ;
int ic ;
while( (ic = isr.read()) != -1 )
{
line.append((char)ic) ;
}
}catch (Exception ioe)
{
System.out.println(ioe);
}finally
{
try
{
if(conn!=null)
conn.close();
}catch(Exception e){}
}
Alert al = new Alert("查询结果",line.toString(),null,AlertType.CONFIRMATION);
al.setTimeout(Alert.FOREVER) ;
display.setCurrent(al) ;
}
}
可以了,在运行代码,就会看到模拟同样出现提示,但是确认后,模拟器会走本地的网络,链接站点。
OK,成功在模拟器上访问了。
注意,这仅仅是模拟器,部署到手机上,要对程序稍加改动,才能用。
在中国移动提供的网络连接中,分为CMNET和CMWAP两种,其中CMNET可以无限制的访问互联网络,资费比较贵。CMWAP类似一个HTTP的代码,只能访问支持HTTP的应用,但是资费便宜,稳定性比较差。
在实际的J2ME网络编程中,一般需要提供以CMWAP代理的方式连接网络,在J2ME中,连接的代码和直接连接有所不同,代码如下:
HttpConnection http = (HttpConnection)Connector.open(("http://10.0.0.172/"+url);
http.setRequestProperty("X-Online-Host",ServerName);
例如你需要访问的地址为:http://www.test.com/login/loginServlet则上面的代码就为:
HttpConnection http = (HttpConnection)Connector.open(("http://10.0.0.172/" + "login/loginServlet");
http.setRequestProperty("X-Online-Host","www.test.com");
在实际使用过程中,只需要使用实际需要访问的地址的域名或者IP来代替ServerName,例如示例中的“www.test.com”,使用后续的地址类代替代码中的url,例如示例中的“login/loginServlet”,就可以实际的使用CMWAP代理来进行连接了。
呜呼,休息一下,在达内学习完C++,最强大的多范型语言,学习J2ME只需要一周就足够了。好比是九阳神功在体内,无所不能。阿,哈哈哈。Java乃是乾坤大挪移。
posted on 2006-02-05 13:28
北国狼人的BloG 阅读(4973)
评论(0) 编辑 收藏 所属分类:
达内学习总结