編輯:關於Android編程
package com.techrare.utils; import java.io.BufferedInputStream; import java.io.BufferedReader; import java.io.ByteArrayInputStream; import java.io.File; import java.io.FileInputStream; import java.io.IOException; import java.io.InputStreamReader; import java.net.URL; import java.net.URLConnection; import java.util.ArrayList; import java.util.Collection; import java.util.HashMap; import java.util.Iterator; import java.util.List; import java.util.Map; import org.jivesoftware.smack.ConnectionConfiguration; import org.jivesoftware.smack.PacketCollector; import org.jivesoftware.smack.Roster; import org.jivesoftware.smack.RosterEntry; import org.jivesoftware.smack.RosterGroup; import org.jivesoftware.smack.SmackConfiguration; import org.jivesoftware.smack.XMPPConnection; import org.jivesoftware.smack.XMPPException; import org.jivesoftware.smack.filter.AndFilter; import org.jivesoftware.smack.filter.PacketFilter; import org.jivesoftware.smack.filter.PacketIDFilter; import org.jivesoftware.smack.filter.PacketTypeFilter; import org.jivesoftware.smack.packet.IQ; import org.jivesoftware.smack.packet.Message; import org.jivesoftware.smack.packet.Packet; import org.jivesoftware.smack.packet.Presence; import org.jivesoftware.smack.packet.Registration; import org.jivesoftware.smack.provider.PrivacyProvider; import org.jivesoftware.smack.provider.ProviderManager; import org.jivesoftware.smack.util.StringUtils; import org.jivesoftware.smackx.Form; import org.jivesoftware.smackx.FormField; import org.jivesoftware.smackx.GroupChatInvitation; import org.jivesoftware.smackx.OfflineMessageManager; import org.jivesoftware.smackx.PrivateDataManager; import org.jivesoftware.smackx.ReportedData; import org.jivesoftware.smackx.ReportedData.Row; import org.jivesoftware.smackx.ServiceDiscoveryManager; import org.jivesoftware.smackx.bytestreams.socks5.provider.BytestreamsProvider; import org.jivesoftware.smackx.filetransfer.FileTransferManager; import org.jivesoftware.smackx.filetransfer.OutgoingFileTransfer; import org.jivesoftware.smackx.muc.DiscussionHistory; import org.jivesoftware.smackx.muc.HostedRoom; import org.jivesoftware.smackx.muc.MultiUserChat; import org.jivesoftware.smackx.packet.ChatStateExtension; import org.jivesoftware.smackx.packet.LastActivity; import org.jivesoftware.smackx.packet.OfflineMessageInfo; import org.jivesoftware.smackx.packet.OfflineMessageRequest; import org.jivesoftware.smackx.packet.SharedGroupsInfo; import org.jivesoftware.smackx.packet.VCard; import org.jivesoftware.smackx.provider.AdHocCommandDataProvider; import org.jivesoftware.smackx.provider.DataFormProvider; import org.jivesoftware.smackx.provider.DelayInformationProvider; import org.jivesoftware.smackx.provider.DiscoverInfoProvider; import org.jivesoftware.smackx.provider.DiscoverItemsProvider; import org.jivesoftware.smackx.provider.MUCAdminProvider; import org.jivesoftware.smackx.provider.MUCOwnerProvider; import org.jivesoftware.smackx.provider.MUCUserProvider; import org.jivesoftware.smackx.provider.MessageEventProvider; import org.jivesoftware.smackx.provider.MultipleAddressesProvider; import org.jivesoftware.smackx.provider.RosterExchangeProvider; import org.jivesoftware.smackx.provider.StreamInitiationProvider; import org.jivesoftware.smackx.provider.VCardProvider; import org.jivesoftware.smackx.provider.XHTMLExtensionProvider; import org.jivesoftware.smackx.search.UserSearch; import org.jivesoftware.smackx.search.UserSearchManager; import android.graphics.drawable.Drawable; import android.util.Log; import com.techrare.listener.TaxiConnectionListener; /** * XmppConnection 工具類 * @author 肖賽SoAi * */ public class XmppConnection { private int SERVER_PORT = 5222; private String SERVER_HOST = "127.0.0.1"; private XMPPConnection connection = null; private String SERVER_NAME = "ubuntuserver4java"; private static XmppConnection xmppConnection = new XmppConnection(); private TaxiConnectionListener connectionListener; /** * 單例模式 * * @return */ synchronized public static XmppConnection getInstance() { return xmppConnection; } /** * 創建連接 */ public XMPPConnection getConnection() { if (connection == null) { openConnection(); } return connection; } /** * 打開連接 */ public boolean openConnection() { try { if (null == connection || !connection.isAuthenticated()) { XMPPConnection.DEBUG_ENABLED = true;// 開啟DEBUG模式 // 配置連接 ConnectionConfiguration config = new ConnectionConfiguration( SERVER_HOST, SERVER_PORT, SERVER_NAME); config.setReconnectionAllowed(true); config.setSecurityMode(ConnectionConfiguration.SecurityMode.disabled); config.setSendPresence(true); // 狀態設為離線,目的為了取離線消息 config.setSASLAuthenticationEnabled(false); // 是否啟用安全驗證 config.setTruststorePath("/system/etc/security/cacerts.bks"); config.setTruststorePassword("changeit"); config.setTruststoreType("bks"); connection = new XMPPConnection(config); connection.connect();// 連接到服務器 // 配置各種Provider,如果不配置,則會無法解析數據 configureConnection(ProviderManager.getInstance()); return true; } } catch (XMPPException xe) { xe.printStackTrace(); connection = null; } return false; } /** * 關閉連接 */ public void closeConnection() { if(connection!=null){ //移除連接監聽 //connection.removeConnectionListener(connectionListener); if(connection.isConnected()) connection.disconnect(); connection = null; } Log.i("XmppConnection", "關閉連接"); } /** * 登錄 * * @param account * 登錄帳號 * @param password * 登錄密碼 * @return */ public boolean login(String account, String password) { try { if (getConnection() == null) return false; getConnection().login(account, password); // 更改在綫狀態 Presence presence = new Presence(Presence.Type.available); getConnection().sendPacket(presence); // 添加連接監聽 connectionListener = new TaxiConnectionListener(); getConnection().addConnectionListener(connectionListener); return true; } catch (XMPPException xe) { xe.printStackTrace(); } return false; } /** * 注冊 * * @param account * 注冊帳號 * @param password * 注冊密碼 * @return 1、注冊成功 0、服務器沒有返回結果2、這個賬號已經存在3、注冊失敗 */ public String regist(String account, String password) { if (getConnection() == null) return "0"; Registration reg = new Registration(); reg.setType(IQ.Type.SET); reg.setTo(getConnection().getServiceName()); // 注意這裡createAccount注冊時,參數是UserName,不是jid,是"@"前面的部分。 reg.setUsername(account); reg.setPassword(password); // 這邊addAttribute不能為空,否則出錯。所以做個標志是android手機創建的吧!!!!! reg.addAttribute("android", "geolo_createUser_android"); PacketFilter filter = new AndFilter(new PacketIDFilter( reg.getPacketID()), new PacketTypeFilter(IQ.class)); PacketCollector collector = getConnection().createPacketCollector( filter); getConnection().sendPacket(reg); IQ result = (IQ) collector.nextResult(SmackConfiguration .getPacketReplyTimeout()); // Stop queuing results停止請求results(是否成功的結果) collector.cancel(); if (result == null) { Log.e("regist", "No response from server."); return "0"; } else if (result.getType() == IQ.Type.RESULT) { Log.v("regist", "regist success."); return "1"; } else { // if (result.getType() == IQ.Type.ERROR) if (result.getError().toString().equalsIgnoreCase("conflict(409)")) { Log.e("regist", "IQ.Type.ERROR: " + result.getError().toString()); return "2"; } else { Log.e("regist", "IQ.Type.ERROR: " + result.getError().toString()); return "3"; } } } /** * 更改用戶狀態 */ public void setPresence(int code) { XMPPConnection con = getConnection(); if (con == null) return; Presence presence; switch (code) { case 0: presence = new Presence(Presence.Type.available); con.sendPacket(presence); Log.v("state", "設置在線"); break; case 1: presence = new Presence(Presence.Type.available); presence.setMode(Presence.Mode.chat); con.sendPacket(presence); Log.v("state", "設置Q我吧"); break; case 2: presence = new Presence(Presence.Type.available); presence.setMode(Presence.Mode.dnd); con.sendPacket(presence); Log.v("state", "設置忙碌"); break; case 3: presence = new Presence(Presence.Type.available); presence.setMode(Presence.Mode.away); con.sendPacket(presence); Log.v("state", "設置離開"); break; case 4: Roster roster = con.getRoster(); Collection<RosterEntry> entries = roster.getEntries(); for (RosterEntry entry : entries) { presence = new Presence(Presence.Type.unavailable); presence.setPacketID(Packet.ID_NOT_AVAILABLE); presence.setFrom(con.getUser()); presence.setTo(entry.getUser()); con.sendPacket(presence); Log.v("state", presence.toXML()); } // 向同一用戶的其他客戶端發送隱身狀態 presence = new Presence(Presence.Type.unavailable); presence.setPacketID(Packet.ID_NOT_AVAILABLE); presence.setFrom(con.getUser()); presence.setTo(StringUtils.parseBareAddress(con.getUser())); con.sendPacket(presence); Log.v("state", "設置隱身"); break; case 5: presence = new Presence(Presence.Type.unavailable); con.sendPacket(presence); Log.v("state", "設置離線"); break; default: break; } } /** * 獲取所有組 * * @return 所有組集合 */ public List<RosterGroup> getGroups() { if (getConnection() == null) return null; List<RosterGroup> grouplist = new ArrayList<RosterGroup>(); Collection<RosterGroup> rosterGroup = getConnection().getRoster() .getGroups(); Iterator<RosterGroup> i = rosterGroup.iterator(); while (i.hasNext()) { grouplist.add(i.next()); } return grouplist; } /** * 獲取某個組裡面的所有好友 * * @param roster * @param groupName * 組名 * @return */ public List<RosterEntry> getEntriesByGroup(String groupName) { if (getConnection() == null) return null; List<RosterEntry> Entrieslist = new ArrayList<RosterEntry>(); RosterGroup rosterGroup = getConnection().getRoster().getGroup( groupName); Collection<RosterEntry> rosterEntry = rosterGroup.getEntries(); Iterator<RosterEntry> i = rosterEntry.iterator(); while (i.hasNext()) { Entrieslist.add(i.next()); } return Entrieslist; } /** * 獲取所有好友信息 * * @return */ public List<RosterEntry> getAllEntries() { if (getConnection() == null) return null; List<RosterEntry> Entrieslist = new ArrayList<RosterEntry>(); Collection<RosterEntry> rosterEntry = getConnection().getRoster() .getEntries(); Iterator<RosterEntry> i = rosterEntry.iterator(); while (i.hasNext()) { Entrieslist.add(i.next()); } return Entrieslist; } /** * 獲取用戶VCard信息 * * @param connection * @param user * @return * @throws XMPPException */ public VCard getUserVCard(String user) { if (getConnection() == null) return null; VCard vcard = new VCard(); try { vcard.load(getConnection(), user); } catch (XMPPException e) { e.printStackTrace(); } return vcard; } /** * 獲取用戶頭像信息 * * @param connection * @param user * @return */ public Drawable getUserImage(String user) { if (getConnection() == null) return null; ByteArrayInputStream bais = null; try { VCard vcard = new VCard(); // 加入這句代碼,解決No VCard for ProviderManager.getInstance().addIQProvider("vCard", "vcard-temp", new org.jivesoftware.smackx.provider.VCardProvider()); if (user == "" || user == null || user.trim().length() <= 0) { return null; } vcard.load(getConnection(), user + "@" + getConnection().getServiceName()); if (vcard == null || vcard.getAvatar() == null) return null; bais = new ByteArrayInputStream(vcard.getAvatar()); } catch (Exception e) { e.printStackTrace(); return null; } return FormatTools.getInstance().InputStream2Drawable(bais); } /** * 添加一個分組 * * @param groupName * @return */ public boolean addGroup(String groupName) { if (getConnection() == null) return false; try { getConnection().getRoster().createGroup(groupName); Log.v("addGroup", groupName + "創建成功"); return true; } catch (Exception e) { e.printStackTrace(); return false; } } /** * 刪除分組 * * @param groupName * @return */ public boolean removeGroup(String groupName) { return true; } /** * 添加好友 無分組 * * @param userName * @param name * @return */ public boolean addUser(String userName, String name) { if (getConnection() == null) return false; try { getConnection().getRoster().createEntry(userName, name, null); return true; } catch (Exception e) { e.printStackTrace(); return false; } } /** * 添加好友 有分組 * * @param userName * @param name * @param groupName * @return */ public boolean addUser(String userName, String name, String groupName) { if (getConnection() == null) return false; try { Presence subscription = new Presence(Presence.Type.subscribed); subscription.setTo(userName); userName += "@" + getConnection().getServiceName(); getConnection().sendPacket(subscription); getConnection().getRoster().createEntry(userName, name, new String[] { groupName }); return true; } catch (Exception e) { e.printStackTrace(); return false; } } /** * 刪除好友 * * @param userName * @return */ public boolean removeUser(String userName) { if (getConnection() == null) return false; try { RosterEntry entry = null; if (userName.contains("@")) entry = getConnection().getRoster().getEntry(userName); else entry = getConnection().getRoster().getEntry( userName + "@" + getConnection().getServiceName()); if (entry == null) entry = getConnection().getRoster().getEntry(userName); getConnection().getRoster().removeEntry(entry); return true; } catch (Exception e) { e.printStackTrace(); return false; } } /** * 查詢用戶 * * @param userName * @return * @throws XMPPException */ public List<HashMap<String, String>> searchUsers(String userName) { if (getConnection() == null) return null; HashMap<String, String> user = null; List<HashMap<String, String>> results = new ArrayList<HashMap<String, String>>(); try { new ServiceDiscoveryManager(getConnection()); UserSearchManager usm = new UserSearchManager(getConnection()); Form searchForm = usm.getSearchForm(getConnection() .getServiceName()); Form answerForm = searchForm.createAnswerForm(); answerForm.setAnswer("userAccount", true); answerForm.setAnswer("userPhote", userName); ReportedData data = usm.getSearchResults(answerForm, "search" + getConnection().getServiceName()); Iterator<Row> it = data.getRows(); Row row = null; while (it.hasNext()) { user = new HashMap<String, String>(); row = it.next(); user.put("userAccount", row.getValues("userAccount").next() .toString()); user.put("userPhote", row.getValues("userPhote").next() .toString()); results.add(user); // 若存在,則有返回,UserName一定非空,其他兩個若是有設,一定非空 } } catch (XMPPException e) { e.printStackTrace(); } return results; } /** * 修改心情 * * @param connection * @param status */ public void changeStateMessage(String status) { if (getConnection() == null) return; Presence presence = new Presence(Presence.Type.available); presence.setStatus(status); getConnection().sendPacket(presence); } /** * 修改用戶頭像 * * @param file */ public boolean changeImage(File file) { if (getConnection() == null) return false; try { VCard vcard = new VCard(); vcard.load(getConnection()); byte[] bytes; bytes = getFileBytes(file); String encodedImage = StringUtils.encodeBase64(bytes); vcard.setAvatar(bytes, encodedImage); vcard.setEncodedImage(encodedImage); vcard.setField("PHOTO", "<TYPE>image/jpg</TYPE><BINVAL>" + encodedImage + "</BINVAL>", true); ByteArrayInputStream bais = new ByteArrayInputStream( vcard.getAvatar()); FormatTools.getInstance().InputStream2Bitmap(bais); vcard.save(getConnection()); return true; } catch (Exception e) { e.printStackTrace(); return false; } } /** * 文件轉字節 * * @param file * @return * @throws IOException */ private byte[] getFileBytes(File file) throws IOException { BufferedInputStream bis = null; try { bis = new BufferedInputStream(new FileInputStream(file)); int bytes = (int) file.length(); byte[] buffer = new byte[bytes]; int readBytes = bis.read(buffer); if (readBytes != buffer.length) { throw new IOException("Entire file not read"); } return buffer; } finally { if (bis != null) { bis.close(); } } } /** * 刪除當前用戶 * * @return */ public boolean deleteAccount() { if (getConnection() == null) return false; try { getConnection().getAccountManager().deleteAccount(); return true; } catch (XMPPException e) { return false; } } /** * 修改密碼 * * @return */ public boolean changePassword(String pwd) { if (getConnection() == null) return false; try { getConnection().getAccountManager().changePassword(pwd); return true; } catch (XMPPException e) { return false; } } /** * 初始化會議室列表 */ public List<HostedRoom> getHostRooms() { if (getConnection() == null) return null; Collection<HostedRoom> hostrooms = null; List<HostedRoom> roominfos = new ArrayList<HostedRoom>(); try { new ServiceDiscoveryManager(getConnection()); hostrooms = MultiUserChat.getHostedRooms(getConnection(), getConnection().getServiceName()); for (HostedRoom entry : hostrooms) { roominfos.add(entry); Log.i("room", "名字:" + entry.getName() + " - ID:" + entry.getJid()); } Log.i("room", "服務會議數量:" + roominfos.size()); } catch (XMPPException e) { e.printStackTrace(); } return roominfos; } /** * 創建房間 * * @param roomName * 房間名稱 */ public MultiUserChat createRoom(String user, String roomName, String password) { if (getConnection() == null) return null; MultiUserChat muc = null; try { // 創建一個MultiUserChat muc = new MultiUserChat(getConnection(), roomName + "@conference." + getConnection().getServiceName()); // 創建聊天室 muc.create(roomName); // 獲得聊天室的配置表單 Form form = muc.getConfigurationForm(); // 根據原始表單創建一個要提交的新表單。 Form submitForm = form.createAnswerForm(); // 向要提交的表單添加默認答復 for (Iterator<FormField> fields = form.getFields(); fields .hasNext();) { FormField field = (FormField) fields.next(); if (!FormField.TYPE_HIDDEN.equals(field.getType()) && field.getVariable() != null) { // 設置默認值作為答復 submitForm.setDefaultAnswer(field.getVariable()); } } // 設置聊天室的新擁有者 List<String> owners = new ArrayList<String>(); owners.add(getConnection().getUser());// 用戶JID submitForm.setAnswer("muc#roomconfig_roomowners", owners); // 設置聊天室是持久聊天室,即將要被保存下來 submitForm.setAnswer("muc#roomconfig_persistentroom", true); // 房間僅對成員開放 submitForm.setAnswer("muc#roomconfig_membersonly", false); // 允許占有者邀請其他人 submitForm.setAnswer("muc#roomconfig_allowinvites", true); if (!password.equals("")) { // 進入是否需要密碼 submitForm.setAnswer("muc#roomconfig_passwordprotectedroom", true); // 設置進入密碼 submitForm.setAnswer("muc#roomconfig_roomsecret", password); } // 能夠發現占有者真實 JID 的角色 // submitForm.setAnswer("muc#roomconfig_whois", "anyone"); // 登錄房間對話 submitForm.setAnswer("muc#roomconfig_enablelogging", true); // 僅允許注冊的昵稱登錄 submitForm.setAnswer("x-muc#roomconfig_reservednick", true); // 允許使用者修改昵稱 submitForm.setAnswer("x-muc#roomconfig_canchangenick", false); // 允許用戶注冊房間 submitForm.setAnswer("x-muc#roomconfig_registration", false); // 發送已完成的表單(有默認值)到服務器來配置聊天室 muc.sendConfigurationForm(submitForm); } catch (XMPPException e) { e.printStackTrace(); return null; } return muc; } /** * 加入會議室 * * @param user * 昵稱 * @param password * 會議室密碼 * @param roomsName * 會議室名 */ public MultiUserChat joinMultiUserChat(String user, String roomsName, String password) { if (getConnection() == null) return null; try { // 使用XMPPConnection創建一個MultiUserChat窗口 MultiUserChat muc = new MultiUserChat(getConnection(), roomsName + "@conference." + getConnection().getServiceName()); // 聊天室服務將會決定要接受的歷史記錄數量 DiscussionHistory history = new DiscussionHistory(); history.setMaxChars(0); // history.setSince(new Date()); // 用戶加入聊天室 muc.join(user, password, history, SmackConfiguration.getPacketReplyTimeout()); Log.i("MultiUserChat", "會議室【"+roomsName+"】加入成功........"); return muc; } catch (XMPPException e) { e.printStackTrace(); Log.i("MultiUserChat", "會議室【"+roomsName+"】加入失敗........"); return null; } } /** * 查詢會議室成員名字 * * @param muc */ public List<String> findMulitUser(MultiUserChat muc) { if (getConnection() == null) return null; List<String> listUser = new ArrayList<String>(); Iterator<String> it = muc.getOccupants(); // 遍歷出聊天室人員名稱 while (it.hasNext()) { // 聊天室成員名字 String name = StringUtils.parseResource(it.next()); listUser.add(name); } return listUser; } /** * 發送文件 * * @param user * @param filePath */ public void sendFile(String user, String filePath) { if (getConnection() == null) return; // 創建文件傳輸管理器 FileTransferManager manager = new FileTransferManager(getConnection()); // 創建輸出的文件傳輸 OutgoingFileTransfer transfer = manager .createOutgoingFileTransfer(user); // 發送文件 try { transfer.sendFile(new File(filePath), "You won't believe this!"); } catch (XMPPException e) { e.printStackTrace(); } } /** * 獲取離線消息 * * @return */ public Map<String, List<HashMap<String, String>>> getHisMessage() { if (getConnection() == null) return null; Map<String, List<HashMap<String, String>>> offlineMsgs = null; try { OfflineMessageManager offlineManager = new OfflineMessageManager( getConnection()); Iterator<Message> it = offlineManager.getMessages(); int count = offlineManager.getMessageCount(); if (count <= 0) return null; offlineMsgs = new HashMap<String, List<HashMap<String, String>>>(); while (it.hasNext()) { Message message = it.next(); String fromUser = StringUtils.parseName(message.getFrom()); ; HashMap<String, String> histrory = new HashMap<String, String>(); histrory.put("useraccount", StringUtils.parseName(getConnection().getUser())); histrory.put("friendaccount", fromUser); histrory.put("info", message.getBody()); histrory.put("type", "left"); if (offlineMsgs.containsKey(fromUser)) { offlineMsgs.get(fromUser).add(histrory); } else { List<HashMap<String, String>> temp = new ArrayList<HashMap<String, String>>(); temp.add(histrory); offlineMsgs.put(fromUser, temp); } } offlineManager.deleteMessages(); } catch (Exception e) { e.printStackTrace(); } return offlineMsgs; } /** * 判斷OpenFire用戶的狀態 strUrl : * url格式 - http://my.openfire.com:9090/plugins/presence * /status?jid=user1@SERVER_NAME&type=xml * 返回值 : 0 - 用戶不存在; 1 - 用戶在線; 2 - 用戶離線 * 說明 :必須要求 OpenFire加載 presence 插件,同時設置任何人都可以訪問 */ public int IsUserOnLine(String user) { String url = "http://"+SERVER_HOST+":9090/plugins/presence/status?" + "jid="+ user +"@"+ SERVER_NAME +"&type=xml"; int shOnLineState = 0; // 不存在 try { URL oUrl = new URL(url); URLConnection oConn = oUrl.openConnection(); if (oConn != null) { BufferedReader oIn = new BufferedReader(new InputStreamReader( oConn.getInputStream())); if (null != oIn) { String strFlag = oIn.readLine(); oIn.close(); System.out.println("strFlag"+strFlag); if (strFlag.indexOf("type=\"unavailable\"") >= 0) { shOnLineState = 2; } if (strFlag.indexOf("type=\"error\"") >= 0) { shOnLineState = 0; } else if (strFlag.indexOf("priority") >= 0 || strFlag.indexOf("id=\"") >= 0) { shOnLineState = 1; } } } } catch (Exception e) { e.printStackTrace(); } return shOnLineState; } /** * 加入providers的函數 ASmack在/META-INF缺少一個smack.providers 文件 * * @param pm */ public void configureConnection(ProviderManager pm) { // Private Data Storage pm.addIQProvider("query", "jabber:iq:private", new PrivateDataManager.PrivateDataIQProvider()); // Time try { pm.addIQProvider("query", "jabber:iq:time", Class.forName("org.jivesoftware.smackx.packet.Time")); } catch (ClassNotFoundException e) { Log.w("TestClient", "Can't load class for org.jivesoftware.smackx.packet.Time"); } // Roster Exchange pm.addExtensionProvider("x", "jabber:x:roster", new RosterExchangeProvider()); // Message Events pm.addExtensionProvider("x", "jabber:x:event", new MessageEventProvider()); // Chat State pm.addExtensionProvider("active", "http://jabber.org/protocol/chatstates", new ChatStateExtension.Provider()); pm.addExtensionProvider("composing", "http://jabber.org/protocol/chatstates", new ChatStateExtension.Provider()); pm.addExtensionProvider("paused", "http://jabber.org/protocol/chatstates", new ChatStateExtension.Provider()); pm.addExtensionProvider("inactive", "http://jabber.org/protocol/chatstates", new ChatStateExtension.Provider()); pm.addExtensionProvider("gone", "http://jabber.org/protocol/chatstates", new ChatStateExtension.Provider()); // XHTML pm.addExtensionProvider("html", "http://jabber.org/protocol/xhtml-im", new XHTMLExtensionProvider()); // Group Chat Invitations pm.addExtensionProvider("x", "jabber:x:conference", new GroupChatInvitation.Provider()); // Service Discovery # Items pm.addIQProvider("query", "http://jabber.org/protocol/disco#items", new DiscoverItemsProvider()); // Service Discovery # Info pm.addIQProvider("query", "http://jabber.org/protocol/disco#info", new DiscoverInfoProvider()); // Data Forms pm.addExtensionProvider("x", "jabber:x:data", new DataFormProvider()); // MUC User pm.addExtensionProvider("x", "http://jabber.org/protocol/muc#user", new MUCUserProvider()); // MUC Admin pm.addIQProvider("query", "http://jabber.org/protocol/muc#admin", new MUCAdminProvider()); // MUC Owner pm.addIQProvider("query", "http://jabber.org/protocol/muc#owner", new MUCOwnerProvider()); // Delayed Delivery pm.addExtensionProvider("x", "jabber:x:delay", new DelayInformationProvider()); // Version try { pm.addIQProvider("query", "jabber:iq:version", Class.forName("org.jivesoftware.smackx.packet.Version")); } catch (ClassNotFoundException e) { // Not sure what's happening here. } // VCard pm.addIQProvider("vCard", "vcard-temp", new VCardProvider()); // Offline Message Requests pm.addIQProvider("offline", "http://jabber.org/protocol/offline", new OfflineMessageRequest.Provider()); // Offline Message Indicator pm.addExtensionProvider("offline", "http://jabber.org/protocol/offline", new OfflineMessageInfo.Provider()); // Last Activity pm.addIQProvider("query", "jabber:iq:last", new LastActivity.Provider()); // User Search pm.addIQProvider("query", "jabber:iq:search", new UserSearch.Provider()); // SharedGroupsInfo pm.addIQProvider("sharedgroup", "http://www.jivesoftware.org/protocol/sharedgroup", new SharedGroupsInfo.Provider()); // JEP-33: Extended Stanza Addressing pm.addExtensionProvider("addresses", "http://jabber.org/protocol/address", new MultipleAddressesProvider()); // FileTransfer pm.addIQProvider("si", "http://jabber.org/protocol/si", new StreamInitiationProvider()); pm.addIQProvider("query", "http://jabber.org/protocol/bytestreams", new BytestreamsProvider()); // Privacy pm.addIQProvider("query", "jabber:iq:privacy", new PrivacyProvider()); pm.addIQProvider("command", "http://jabber.org/protocol/commands", new AdHocCommandDataProvider()); pm.addExtensionProvider("malformed-action", "http://jabber.org/protocol/commands", new AdHocCommandDataProvider.MalformedActionError()); pm.addExtensionProvider("bad-locale", "http://jabber.org/protocol/commands", new AdHocCommandDataProvider.BadLocaleError()); pm.addExtensionProvider("bad-payload", "http://jabber.org/protocol/commands", new AdHocCommandDataProvider.BadPayloadError()); pm.addExtensionProvider("bad-sessionid", "http://jabber.org/protocol/commands", new AdHocCommandDataProvider.BadSessionIDError()); pm.addExtensionProvider("session-expired", "http://jabber.org/protocol/commands", new AdHocCommandDataProvider.SessionExpiredError()); } }
調用該工具類的方法很簡單,用了一個單例模式,裡面的方法都可以用相同的方法調用
XmppConnection.getInstance().login(username,password)
前一篇博客分析了Native端向Javascript端通信的全流程,這次來研究下Javascript端向Native端通信的全流程,與前篇恰好構成一個基本完整的通信機制。
效果圖: public SimpleAdapter(Context context, List extends Map data, int resou
ool1手機的亮點在於雙攝2.0技術的1300萬雙後置鏡頭,系統也進化到樂視EUI。這樣的一款手機很多人很好奇它和年初發布的樂視2超級手機哪個好?那麼到底c
先說明一下,項目代碼已上傳至github,不想看長篇大論的也可以先去下代碼,對照代碼,哪裡不懂點哪裡。代碼在這https://github.com/zgzczzw/ZHF