1. 文件的发送
开一个文件选择框,选中文件后再调用下面的方法
- public static void sendFile(XMPPConnection connection,
- String user, File file) throws XMPPException, InterruptedException {
- System.out.println("发送文件开始"+file.getName());
- FileTransferManager transfer = new FileTransferManager(Client.getConnection());
- System.out.println("发送文件给: "+user+Client.getServiceNameWithPre());
- OutgoingFileTransfer out = transfer.createOutgoingFileTransfer(user+Client.getServiceNameWithPre()+"/Smack");//
- out.sendFile(file, file.getName());
- System.out.println("//////////");
- System.out.println(out.getStatus());
- System.out.println(out.getProgress());
- System.out.println(out.isDone());
- System.out.println("//////////");
- System.out.println("发送文件结束");
- }
2. 文件接收,必须使用监听
- FileTransferManager transfer = new FileTransferManager(connection);
- transfer.addFileTransferListener(new RecFileTransferListener());
- public class RecFileTransferListener implements FileTransferListener {
- public String getFileType(String fileFullName)
- {
- if(fileFullName.contains("."))
- {
- return "."+fileFullName.split("//.")[1];
- }else{
- return fileFullName;
- }
- }
- @Override
- public void fileTransferRequest(FileTransferRequest request) {
- System.out.println("接收文件开始.....");
- final IncomingFileTransfer inTransfer = request.accept();
- final String fileName = request.getFileName();
- long length = request.getFileSize();
- final String fromUser = request.getRequestor().split("/")[0];
- System.out.println("文件大小:"+length + " "+request.getRequestor());
- System.out.println(""+request.getMimeType());
- try {
- JFileChooser chooser = new JFileChooser();
- chooser.setCurrentDirectory(new File("."));
- int result = chooser.showOpenDialog(null);
- if(result==JFileChooser.APPROVE_OPTION)
- {
- final File file = chooser.getSelectedFile();
- System.out.println(file.getAbsolutePath());
- new Thread(){
- public void run()
- {
- try {
- System.out.println("接受文件: " + fileName);
- inTransfer
- .recieveFile(new File(file
- .getAbsolutePath()
- + getFileType(fileName)));
- Message message = new Message();
- message.setFrom(fromUser);
- message.setProperty("REC_SIGN", "SUCCESS");
- message.setBody("["+fromUser+"]发送文件: "+fileName+"/r/n"+"存储位置: "+file.getAbsolutePath()+ getFileType(fileName));
- if (Client.isChatExist(fromUser)) {
- Client.getChatRoom(fromUser).messageReceiveHandler(
- message);
- } else {
- ChatFrameThread cft = new ChatFrameThread(
- fromUser, message);
- cft.start();
- }
- } catch (Exception e2) {
- e2.printStackTrace();
- }
- }
- }.start();
- }else{
- System.out.println("拒绝接受文件: "+fileName);
- request.reject();
- Message message = new Message();
- message.setFrom(fromUser);
- message.setBody("拒绝"+fromUser+"发送文件: "+fileName);
- message.setProperty("REC_SIGN", "REJECT");
- if (Client.isChatExist(fromUser)) {
- Client.getChatRoom(fromUser)
- .messageReceiveHandler(message);
- } else {
- ChatFrameThread cft = new ChatFrameThread(
- fromUser, message);
- cft.start();
- }
- }
- /* InputStream in = inTransfer.recieveFile();
- String fileName = "r"+inTransfer.getFileName();
- OutputStream out = new FileOutputStream(new File("d:/receive/"+fileName));
- byte[] b = new byte[512];
- while(in.read(b) != -1)
- {
- out.write(b);
- out.flush();
- }
- in.close();
- out.close();*/
- } catch (Exception e) {
- e.printStackTrace();
- }
- System.out.println("接收文件结束.....");
- }
- }
1.离线消息
openfire本身是支持离线消息的,不需要进行额外处理,可以用spark测试下
使用smack,其实他提供了相应的方法
Class OfflineMessageManager
可以看下描述
The OfflineMessageManager helps manage offline messages even before the user has sent an available presence. When a user asks for his offline messages before sending an available presence then the server will not send a flood with all the offline messages when the user becomes online. The server will not send a flood with all the offline messages to the session that made the offline messages request or to any other session used by the user that becomes online.
英文退化了点,汗,大意就是,必须在发送在线信息之前去获取离线消息
刚开始没看这个,结果在上线之后,去取,结果。。。。离线消息数量总是为零,囧
首先,连接,状态要设为离线
- ConnectionConfiguration connConfig = new ConnectionConfiguration(serverDomain);
- connConfig.setSendPresence(false); // where connConfig is object of .
- connection = new XMPPConnection(connConfig);
- connection.connect();
然后,登陆
connection.login(userName, pwd);
接着,拿离线消息
- OfflineMessageManager offlineManager = new OfflineMessageManager(
- Client.getConnection());
- try {
- Iterator<org.jivesoftware.smack.packet.Message> it = offlineManager
- .getMessages();
- System.out.println(offlineManager.supportsFlexibleRetrieval());
- System.out.println("离线消息数量: " + offlineManager.getMessageCount());
- Map<String,ArrayList<Message>> offlineMsgs = new HashMap<String,ArrayList<Message>>();
- while (it.hasNext()) {
- org.jivesoftware.smack.packet.Message message = it.next();
- System.out
- .println("收到离线消息, Received from 【" + message.getFrom()
- + "】 message: " + message.getBody());
- String fromUser = message.getFrom().split("/")[0];
- if(offlineMsgs.containsKey(fromUser))
- {
- offlineMsgs.get(fromUser).add(message);
- }else{
- ArrayList<Message> temp = new ArrayList<Message>();
- temp.add(message);
- offlineMsgs.put(fromUser, temp);
- }
- }
- //在这里进行处理离线消息集合......
- Set<String> keys = offlineMsgs.keySet();
- Iterator<String> offIt = keys.iterator();
- while(offIt.hasNext())
- {
- String key = offIt.next();
- ArrayList<Message> ms = offlineMsgs.get(key);
- TelFrame tel = new TelFrame(key);
- ChatFrameThread cft = new ChatFrameThread(key, null);
- cft.setTel(tel);
- cft.start();
- for (int i = 0; i < ms.size(); i++) {
- tel.messageReceiveHandler(ms.get(i));
- }
- }
- offlineManager.deleteMessages();
- } catch (Exception e) {
- e.printStackTrace();
- }
记得最后要把离线消息删除,即通知服务器删除离线消息
offlineManager.deleteMessages();
否则,下次上了消息还存在
接着,上线
Presence presence = new Presence(Presence.Type.available);
connection.sendPacket(presence);
2.离线文件
这个我没实现,汗
主要思想:开发openfire插件,拦截离线文件,将文件存到服务器上,同时在数据库里开一张表,存储文件信息
当用户上线时,查表,若是有,根据路径,拿了发送
当然,大家可以谷歌下是否有相应的插件,时间紧迫,我倒是没找着
到这里,大概就这些了,对了,还扩展了个视频音频聊天,不过使用的是JMF,点对点的,本来打算使用jingle的,结果连API文档都没找到,晕死
就这些
相关推荐
3. 文件传输:通过扩展协议实现文件的发送和接收。 4. 聊天历史:存储和检索聊天记录,实现离线消息功能。 五、Android源码分析 深入研究Android源码,我们可以了解如何在系统层面支持XMPP服务。例如,查看Android...
4. **消息发送和接收**:实现发送和接收XMPP消息的接口。这通常涉及解析和构建XML消息结构,以及监听服务器推送的消息。 5. **事件监听**:注册监听器以响应状态变化(如在线/离线状态)、新消息到达、好友请求等...
XMPP协议的优势在于其灵活性和可扩展性,它允许开发者构建支持多种功能的聊天应用,如一对一聊天、群组聊天、文件传输等。 首先,要理解XMPP的工作原理。XMPP服务器作为核心,负责处理客户端之间的消息传递和状态...
这个压缩包文件“安卓Android源码——基于XMPP的即时聊天项目.zip”包含了关于在安卓平台上构建一个基于XMPP协议的即时聊天应用的资源。XMPP(Extensible Messaging and Presence Protocol,可扩展消息传递和存在...
Smack支持多种特性,包括TLS/SSL加密、多用户聊天室、离线消息处理以及资源管理等。由于它是跨平台的,可以在Java虚拟机运行的任何系统上使用,包括桌面、移动设备甚至是Web应用。 Openfire是另一个与Spark和Smack...
【安卓Android源码——【仿微信即时聊天】xmpp4安卓Android 第一期.rar】这个压缩包文件主要包含了一个安卓应用的源代码,该应用模仿了微信的即时通讯功能。源码的学习可以帮助开发者深入理解Android即时通讯应用的...
开发者可以通过开源库,如Smack、Java Jabber Library(JJlib)等来实现XMPP功能。 为了更好地理解和应用XMPP,需要掌握XML解析、网络编程和相关工具的使用。例如,`xmllint`可以用来验证XML文档的结构,而`xmpp-...
它针对Android环境进行了优化,解决了权限问题,使得Android应用能够无缝地接入XMPP网络,实现聊天、文件传输等功能。 再者,Spark是基于Java的XMPP桌面客户端,它的设计简洁易用,为开发者提供了很好的参考。虽然...
XMPP的核心组件包括Jabber服务器、客户端库以及一系列扩展协议,如XEP(XMPP Extension Protocols),用于实现文件传输、位置共享等高级功能。 在这个开源项目中,"XMPPClient"可能是一个实现了XMPP协议的Android...
Openfire有一个插件——Smack Push,它可以配合这些推送服务,将离线消息推送到客户端。 - 配置Openfire的Smack Push插件,需要在插件管理界面安装并激活,然后配置相应的APNs或GCM/FCM证书。 5. **安全与性能优化...
5. **消息和状态交换**:解释如何发送和接收文本消息,以及如何处理用户的在线状态,如在线、离线、忙碌等。 6. **多用户聊天(MUC)**:介绍如何使用Jabber协议创建和参与多用户聊天室,以及管理权限和角色。 7. ...
AdXmpp通过asmack库来实现对XMPP协议的解析和处理,asmack是Smack库的Android优化版本,能更好地适应Android的环境。 Openfire是基于XMPP协议的服务器软件,它提供了一个可扩展的、高性能的即时通信平台。在我们的...