自己写代码 - HelloHi开发流水账 二 先跑起来
来源:互联网 发布:雪梨的淘宝店是哪个店 编辑:程序博客网 时间:2024/05/16 13:01
刚开始一切随简,先让人能够说话。
Web Application不同于传统的网站在于客户端和程序的交互,然而在这里,随机聊天系统里不再是客户端和服务器的交互,而是客户端和客户端之间交互,服务器为这种交互提供了中转。因此我要做的就是客户端C1发送消息到服务器,然后另外的客户端C2在服务器上取得消息,就可以实现聊天。唯一不爽的是,C1对C2说“Hi”,C2什么时候能听见不取决于C1什么时候说,而是取决于C2什么时候想听,因此这不是实时的。用一个Timer不停的更新可以做出一种貌似实时的样子。
修改RPC接口,看看需要些什么。
客户端要和客户端交互,因此必须要把他们区别开来,每个客户端必须有一个id。因此连上系统第一步需要去取得一个有效的id。之后的通信,服务端都需要区分客户端,因此都要提供客户端id。发送消息只需要再提供一个String表示消息内容就可以了。更新消息的策略值得思考。本着先跑起来的思想,先搞个简单的,每次把所有的消息都拿过来好了,给一个clientId,返回一个String数组。
修改GreetingService,删除原来的String greetServer(String name);添加新的方法。
public interface GreetingService extends RemoteService {
int getClientId();
void sendMessage(int clientId, String message);
String[] updateMessage(int clientId);
}
修改相应的异步接口和实现。
现在这个Service已经不提供Greeting方法,它的名字让我很不爽,Refactor之。改成HelloService。打开web.xml,可以看出service是怎么映射起来的:
<servlet-name>greetServlet</servlet-name>
<servlet-class>com.gmail.hy87cn.server.HelloServiceImpl</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>greetServlet</servlet-name>
<url-pattern>/hellohi/greet</url-pattern>
</servlet-mapping>
我觉得这个路径名和servlet名字也都不合适,改成hello,RemoteServiceRelativePath标注改成“hello”,然后把web.xml里面的也改掉。
在HelloUi里面添加两个字段
private HelloServiceAsync service = GWT.create(HelloService.class);
再添加getClient方法
service.getClientId(new AsyncCallback<Integer>() {
@Override
public void onFailure(Throwable caught) {
// TODO Auto-generated method stub
}
@Override
public void onSuccess(Integer result) {
id = result;
}
});
}
远程调用都是异步方法,并且你是不能肯定调用一定成功的,除了保证代码正确,远程调用是否成功还取决于网络状况,服务器抽风程度等。因此我们不能够get一次clientId就不管了,而是不停的get直到get到有效地id为止。什么时候做这个动作呢,如果想不清楚,姑且就delay到需要clientId的时候。
再添加一个Timer和update方法。
@Override
public void run() {
update();
}
};
if (clientId == -1) {
initClientId();
} else {
service.updateMessage(clientId, new AsyncCallback<String[]>() {
@Override
public void onFailure(Throwable caught) {
// TODO Auto-generated method stub
}
@Override
public void onSuccess(String[] result) {
contentPanel.clear();
for (String message : result) {
contentPanel.add(new HTML(message));
}
}
});
}
}
由于是异步调用,我们不能在initClientId调用后马上调用updateMessage,因为initClientId之后clientId也还不一定就就绪了。
然后在构造函数里加上timer.scheduleRepeating(2000);//ms这句,timer就会开始以2秒为间隔执行run函数,run会调用update。
我总是喜欢刚开始的时候尽量简单,所以连发送消息的按钮都省了,用回车键吧。在构造函数里给inputText添加一个KeyPressHandler,响应按键事件,判断如果是按回车键,就调用sendMessage方法。
@Override
public void onKeyPress(KeyPressEvent event) {
if (event.getCharCode() == KeyCodes.KEY_ENTER) {
sendMessage();
}
}
});
String input = inputText.getText();
if (!input.isEmpty()) {
service.sendMessage(clientId, input, new AsyncCallback<Void>() {
@Override
public void onFailure(Throwable caught) {
// TODO Auto-generated method stub
}
@Override
public void onSuccess(Void result) {
inputText.setText("");
}
});
}
}
如果发消息成功就把inputText清空。
客户端大抵就是这个样子了,很简陋,不过没关系,第一个版本的服务端将会更加简陋。
随机的聊天系统是一对一的,可以想象成两个客户端会进入同一个聊天室,发送信息不是发送给对方,而是发送给聊天室。这里就有两个问题,一是说话的问题,一是分配聊天室的问题。福尔摩斯说一次只考虑一个问题,因此现在我只考虑说话的问题,先搞成所有客户端公用一个聊天室。够简陋了吧。呃,这样一来其实连clientId都可以省了。getClientId直接返回一个0吧,只要不是-1就行。然后sendMessage把这些String存放到一个ArrayList,updateMessages把这些String传回来。
在HelloServiceImpl里面添加private ArrayList<String> messageList = new ArrayList<String>();
然后实现sendMessage方法和updateMessages方法。
public void sendMessage(int clientId, String message) {
messageList.add(message);
}
@Override
public String[] updateMessage(int clientId) {
String[] messageArray = new String[messageList.size()];
return messageList.toArray(messageArray);
}
Run,可以了,开三个网页,说话互相都能看见。虽然消息是谁说的都不知道,陋是陋了点,第一步先这样吧。先更正一些小问题。
1.页面打开后要等2秒钟才会执行第一次update,我希望他一开始先做一次。
2.发送消息后,要等下一次update才会看到自己发出的消息,我希望发送消息之后先update一下。
3.在contentPanel里面添加东西之后把滚动条拖到最后。
在构造函数的timer.scheduleRepeating(2000);//ms之前调用一下timer.schedule(1);,在sendMessage的onSuccess里面调用update,在添加新内容到contentPanel之后,调用scrollPanel.scrollToBottom();
看上去好一点了,不过还是很挫,跑是能跑了,接下来就来解决挫的问题。
- 自己写代码 - HelloHi开发流水账 二 先跑起来
- 自己写代码 - HelloHi开发流水账 一 先画个躯壳
- 自己写代码 - HelloHi开发流水账 四 不止是String
- 自己写代码 - HelloHi开发流水账 五 一枚臭虫
- 自己写代码 - HelloHi开发流水账 三 别再那么二
- 自己写代码 HelloHi开发日记 六 掰开Ui和逻辑
- 自己写的一点福利代码(二)
- 第一篇先自己写
- 让自己跑起来
- 即时消息服务 能不能自己先用起来--客服
- 【流水账】利用闲置笔记本搭建自己的开发服务器
- 写给自己的流水账
- 折线翻页效果,学习起来,最近需要写一个类似效果,先学习起来
- 【腾讯TMQ】和开发一起写代码,让测试左移起来
- 深度学习二:自己写java代码,识别手写数字
- 好想好想找个角落,自己躲起来,写自己的心情
- 【ulua入门】(1) 让lua跑起来,然后利用框架,写自己的逻辑
- mac os下 ionic 2 安装(二),酷炫的hello world 先跑起来!!(运行app)
- PHP——特殊的全局变量
- 给二叉树加中序线索
- discuz__LEARN comm.inc.php (1)
- 自己写代码 - HelloHi开发流水账 一 先画个躯壳
- 用户***/aspnet登陆失败
- 自己写代码 - HelloHi开发流水账 二 先跑起来
- 程序员应该掌握的实用编程技能(之一)
- CCENT.CCNA.ICND.认证考试指南
- 无线网络破解[转]
- ISA2004教程
- POJ2739 Sum of Consecutive Prime Numbers
- Shell编程
- asp.net中提取字符串中所包含的中文
- 从少林寺的核心竞争力看软件作坊和正规军的差异