XMPPFramework (二)

作者: iLeooooo | 来源:发表于2016-05-17 17:30 被阅读192次

    首先我们在工程LWXmppTest中建一个Xmpp的管理类XMPPManager。

    XMPPManager.h文件:

    #import <Foundation/Foundation.h>
    #import "XMPPFramework.h"
    #import "WXMessage.h"
    #import "StatusBuddy.h"
    
    /**
     *  处理聊天消息的代理
     */
    @protocol MessageDelegate <NSObject>
    
    - (void)newMessage:(WXMessage *)message;
    
    @end
    
    /**
     *  处理好友在线状态的代理
     */
    @protocol StatusDelegate <NSObject>
    
    - (void)isOn:(StatusBuddy *)status;
    
    - (void)isOff:(StatusBuddy *)status;
    
    - (void)meOff;
    
    @end
    
    /**
     *  XMPP管理类,管理xmpp的整个生命周期
     */
    @interface XMPPManager : NSObject
    {
        NSString *password;       //保存密码
    }
    
    @property (nonatomic, weak) id <MessageDelegate> msgDelegate;         //消息代理
    @property (nonatomic, weak) id <StatusDelegate> statusDelegate;       //状态代理
    @property (nonatomic, strong, readonly) XMPPStream *xmppStream;       //xmpp通道
    @property (nonatomic, readonly) BOOL xmppisConnect;                   //xmpp是否连接
    
    /**
     *  使用单例模式管理xmpp对象
     *
     *  @return 整个项目唯一xmpp实例
     */
    + (XMPPManager *)sharedXMPPManager;
    
    #pragma mark xmpp公共方法
    
    /**
     *  初始化xmppStream
     */
    - (void)setupXMPPStream;
    
    /**
     *  关闭xmppStream
     */
    - (void)teardownStream;
    
    /**
     *  连接XMPP服务器
     *
     *  @return 是否连接成功
     */
    - (BOOL)connect;
    
    /**
     *  关闭XMPP连接
     */
    - (void)disconnect;
    
    /**
     *  上线
     */
    - (void)goOnline;
    
    /**
     *  下线
     */
    - (void)goOffline;
    
    /**
     *  获取自己的JID
     *
     *  @return 返回自己的JID
     */
    - (NSString *)myJid;
    
    @end
    
    
    
    #import "XMPPManager.h"
    
    @implementation XMPPManager
    
    + (XMPPManager *)sharedXMPPManager
    {
        static dispatch_once_t once;
        static XMPPManager *sharedManager;
        dispatch_once(&once, ^{
            sharedManager = [[XMPPManager alloc] init];
        });
        return sharedManager;
    }
    
    - (void)setupXMPPStream
    {
         //建立通道
         _xmppStream = [[XMPPStream alloc] init];
        //把通道加入代理队列
        [_xmppStream addDelegate:self delegateQueue:dispatch_get_main_queue()];
    }
    
    - (void)teardownStream
    {
        //移除通道,下线
        [_xmppStream removeDelegate:self];
        [_xmppStream disconnect];
        _xmppStream = nil;
    }    
    
    /**
     *  连接服务器(查看服务器是否可连接)
     *
     *  @return 是否连接
     */
    - (BOOL)connect
    {
        //判断通道是否已经连接
        if (![_xmppStream isDisconnected]) {
            return YES;
        }
    
        //获取JID
        NSString *loginJid = [self myJid];
        NSString *pass = [[NSUserDefaults standardUserDefaults] objectForKey:@"weixinPwd"];
        NSString *server = [[NSUserDefaults standardUserDefaults] objectForKey:@"wxserver"];
    
        if (loginJid == nil || pass == nil) {
            NSLog(@"连接XMPP服务器失败");
            return NO;
        }
    
        //通道的用户名
        [_xmppStream setMyJID:[XMPPJID jidWithString:loginJid]];
        //密码保存备用
        password = pass;
        [_xmppStream setHostName:server];
    
        //进行连接,上线
        NSError *error = nil;
        if (![_xmppStream connectWithTimeout:XMPPStreamTimeoutNone error:&error]) {
            NSLog(@"连接XMPP服务器失败");
            return NO;
        }
        NSLog(@"连接XMPP服务器成功");
        return YES;
    }
    
    //获取自己的JID
    -(NSString *)myJid{
        NSString *jid = [[NSUserDefaults standardUserDefaults] objectForKey:@"weixinID"];
        return jid;
    }
    
    - (void)disconnect
    {
        //下线处理
        [self goOffline];
        //关闭通道,断开连接
        [_xmppStream disconnect];
    }
    
    - (void)goOnline
    {
        //发送上线状态
        XMPPPresence *presence = [XMPPPresence presence];
        [[self xmppStream] sendElement:presence];
    }
    
    - (void)goOffline
    {
        //发送下线状态
        XMPPPresence *presence = [XMPPPresence presenceWithType:@"unavailabe"];
        [[self xmppStream] sendElement:presence];
    }
    
    - (BOOL)xmppisConnect
    {
        //判断xmpp是否连接
        return ![_xmppStream isDisconnected];
    }
    
    #pragma mark XMPPStreamDelegate
    
    - (void)xmppStreamDidConnect:(XMPPStream *)sender
    {
        NSError *error = nil;
    
        if (![[self xmppStream] authenticateWithPassword:password error:&error]) {
            NSLog(@"Error authenticating: %@", error);
        }
    }
    
    /**
     *  验证成功,进行上线操作
     *
     *  @param sender
     */
    - (void)xmppStreamDidAuthenticate:(XMPPStream *)sender
    {
        //上线
        [self goOnline];
    }
    
    /**
     *  收到状态
     */
    - (void)xmppStream:(XMPPStream *)sender didReceivePresence:(XMPPPresence *)presence
    {
        NSLog(@"%@", presence);
        //我自己的用户名
        NSString *myuser = sender.myJID.user;
        //好友的用户名
        NSString *user = presence.from.user;
        //用户所在的域
        NSString *domain = presence.from.domain;
        //状态类型
        NSString *type = presence.type;
        //如果状态不是自己的
        if (user != myuser) {
            //初始化状态对象
            StatusBuddy *status = [[StatusBuddy alloc] init];
            //保存了状态的用户名
            status.name = [NSString stringWithFormat:@"%@@%@", user, domain];
            //上线,状态代理
            if ([type isEqualToString:@"available"]) {
                status.isOnline = YES;
                //用户上线,执行上线代理操作
                if ([_statusDelegate respondsToSelector:@selector(isOn:)]) {
                    [_statusDelegate isOn:status];
                }
                //用户下线,执行下线代理操作
            } else if ([type isEqualToString:@"unavailable"]) {
                if ([_statusDelegate respondsToSelector:@selector(isOff:)]) {
                    [_statusDelegate isOff:status];
                }
            }
        } 
    }
    
    /**
     *  收到消息
     */
    - (void)xmppStream:(XMPPStream *)sender didReceiveMessage:(XMPPMessag  *)message
    {
        NSLog(@"%@", message);
        //获取接收消息
        //如果消息是聊天消息
        if (message.isChatMessage) {
            //初始化消息对象
            WXMessage *wxmsg = [[WXMessage alloc] init];
            //对方正在输入
            if ([message elementForName:@"composing"] != nil) {
                wxmsg.isComposing = YES;
            }
            //是否是离线消息
            if ([message elementForName:@"delay"] != nil) {
                wxmsg.isDelay = YES;
            }
            
            //消息正文
            wxmsg.body = [[message elementForName:@"body"] stringValue];
        
            //完整用户名
            wxmsg.from = [NSString stringWithFormat:@"%@@%@", message.from.user, message.from.domain];
            
            //通过代理把消息传出去,在界面进行处理显示
            if ([_msgDelegate respondsToSelector:@selector(newMessage:)]) {
                [_msgDelegate newMessage:wxmsg];
            }
        }
    }
    
    @end
    

    上面的就是对xmpp的消息和状态的部分处理。xmpp还有好多其他的属性,要用的话可以自己添加进去,然后对其进行处理,这里只是xmpp的一些基本的方法的使用。后面的聊天界面我是直接参考小波的swift版的小微信界面。

    聊天界面.png 消息界面.png 即时聊天.png

    要Demo的可以私聊我。

    共勉!一步一个巴掌印。。。。。

    相关文章

      网友评论

        本文标题:XMPPFramework (二)

        本文链接:https://www.haomeiwen.com/subject/qryirttx.html