欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

App内发送短信

程序员文章站 2022-05-31 10:42:16
...

第一: 介绍

                App 内发送短信是不用跳出App利用手机系统的发短信页面直接在本App内就可以发送短信的功能。本功能在         iOS4.0  的时被引入进来,主要是使用   #import <MessageUI/MessageUI.h>    头文件下的  MFMessageComposeViewController  类。


第二、准备工作

          由第一步我们知道要使用App内发送短信我们必须导入  #import <MessageUI/MessageUI.h>   头文件。导入头文件后还必须使调用短息的那个类准守 MFMessageComposeViewControllerDelegate 协议。同时要实现   messageComposeViewController:didFinishWithResult: 该方法。实例代码展示如下:
1、头文件
// 引入头文件
#import <MessageUI/MessageUI.h>

2、协议
@interface SendMessgaeManager : NSObject <MFMessageComposeViewControllerDelegate>{
}

3、协议方法实现
/*!
 发送信息的事件回调处理函数
 */
- (void)messageComposeViewController:(nonnull MFMessageComposeViewController *)controller didFinishWithResult:(MessageComposeResult)result {
    // 是否返回上一个控制器
    BOOL isCanPush = YES;
    // 事件处理
    switch (result) {
            // 用户取消短信发送
        case MessageComposeResultCancelled:{
            [self alertWithMessage:@"用户取消发送短信"];
        }
            break;
            // 短信发送成功
        case MessageComposeResultSent:{
            [self alertWithMessage:@"短信发送成功,请注意查收"];
        }
            break;
            // 短信发送失败
        case MessageComposeResultFailed:{
            [self alertWithMessage:@"短信发送失败,请重新发送"];
            isCanPush = NO;
        }
            break;
        default:
            break;
    }
    if (!isCanPush) {
        return ;
    }
    // 返回上一个控制器
    [controller dismissViewControllerAnimated:YES completion:nil];
}

第三、MFMessageComposeViewController 类的介绍
// 判断是否可以发送短信

+ (BOOL)canSendText;



// 判断是否支持主题短信的发送,该功能必须在iOS7以上使用

+ (BOOL)canSendSubject API_AVAILABLE(ios(7.0));



// 判断是否发送短信是否支持附件,该功能必须在iOS7以上使用

+ (BOOL)canSendAttachments API_AVAILABLE(ios(7.0));



// 判断发送短信附件是否支持系统统一类型标识符(Uniform Type Identifier)

+ (BOOL)isSupportedAttachmentUTI:(NSString *)uti API_AVAILABLE(ios(7.0));



//发送短信要支持的协议,用于发送短信后的结果处理

@property (nonatomic, nullable, assign) id<MFMessageComposeViewControllerDelegate> messageComposeDelegate;



// 该方法是设置发送短信页面的相机和附件按钮是否可用,该功能必须在iOS7以上使用

- (void)disableUserAttachments API_AVAILABLE(ios(7.0));



// 该参数是短信接收人的手机号(如:10086、18801210281……等) 

@property (nonatomic, nullable, copy) NSArray<NSString *> *recipients;



// 该参数是发送信息的内容

@property (nonatomic, nullable, copy) NSString *body;



// 该参数是发送短信的主题,该参数只有短信系统设置主题显示时,才可以显示。iOS7.0 以上可以使用

@property (nonatomic, nullable, copy) NSString *subject API_AVAILABLE(ios(7.0));



// 发送iMessage 短信的消息体对象,iOS10.0 以上可以使用

@property (nonatomic, nullable, copy) MSMessage *message API_AVAILABLE(ios(10.0));



// 发送短信携带的附件的获取数组,iOS7.0 以上可以使用

@property (nonatomic, nullable, readonly, copy) NSArray<NSDictionary *> *attachments API_AVAILABLE(ios(7.0));



// 通过附件的网址和附件的名称来添加附件,iOS7.0 以上可以使用

- (BOOL)addAttachmentURL:(NSURL *)attachmentURL withAlternateFilename:(nullable NSString *)alternateFilename API_AVAILABLE(ios(7.0));



// 通过附件二进制流和统一类型标示符和附件的名字添加附件,iOS7.0 以上可以使用

- (BOOL)addAttachmentData:(NSData *)attachmentData typeIdentifier:(NSString *)uti filename:(NSString *)filename API_AVAILABLE(ios(7.0));



// 短信发送后的结果回调函数,用于处理短信发送后的结果处理

- (void)messageComposeViewController:(MFMessageComposeViewController *)controller didFinishWithResult:(MessageComposeResult)result;

第四、针对App内短信的发送,封装一个 SendMessgaeManager 

1、附件类 Attachment 的介绍
// 附件对象
@interface Attachment :NSObject
// 附件的连接
@property(nonatomic,strong) NSURL * attachmentURl ;
// 附件的文件名,带后缀
@property(nonatomic,strong) NSString * attachmentName ;
// 附件的二进制文件
@property(nonatomic,strong) NSData * attachmentData ;
@end

该附件类的实现如下:
/*!
 附件对象
 */
@implementation Attachment
@end

2、SendMessgaeManager.h 类的介绍
//
//  SendMessgaeManager.h
//  SendMediaMessage
//
//  Created by MAC on 2017/12/11.
//  Copyright © 2017年 NetworkCode小贱. All rights reserved.
//

#import <Foundation/Foundation.h>

// 引入头文件
#import <MessageUI/MessageUI.h>
@interface SendMessgaeManager : NSObject <MFMessageComposeViewControllerDelegate>{
    UIViewController * TagerController ;
}

// 消息的内容
@property(nonatomic,strong) NSString *  bodyString;
// 接受消息的人
@property(nonatomic,strong) NSArray  * recipientArray;
// 设置消息的主题
@property(nonatomic,strong) NSString * subjectString;
// iMessage
@property(nonatomic,strong) MSMessage * iMessage ;
// 附件对象
@property(nonatomic,strong) Attachment * attachment;
// 统一类型标识符(Uniform Type Identifier 的缩写)
@property(nonatomic,strong) NSString * uitString ;
// 是否显示相机和附件按钮(YES:为不显示)
@property(nonatomic,getter=isShowUserAttachment) BOOL isShowUserAttachment ;
// 单利创建
+(instancetype) sendMessage:(UIViewController *)tagerVc ;
// 发送信息
-(void)sendMessageMethod;
@end

3、SendMessgaeManager.m 的介绍
//
//  SendMessgaeManager.m
//  SendMediaMessage
//
//  Created by MAC on 2017/12/11.
//  Copyright © 2017年 NetworkCode小贱. All rights reserved.
//

#import "SendMessgaeManager.h"

#pragma mark 发送短信单利
static SendMessgaeManager * sendMessageManager = nil ;
@implementation SendMessgaeManager

/*!
 创建单利
 */
+(instancetype) sendMessage:(UIViewController*)tagerVc {
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sendMessageManager = [[self alloc]initWith:tagerVc];
        sendMessageManager.attachment = [[Attachment alloc]init];
    });
    return sendMessageManager ;
}

-(id)initWith:(id)tagerVc {
    if (self == [super init]) {
        TagerController = tagerVc ;
    }
    return self ;
}

-(void)sendMessageMethod {
    // 创建消息发送载体
    MFMessageComposeViewController * MessageComposeVc = [MFMessageComposeViewController new];
    // 判断是否有发送消息的功能
    BOOL isCanSend = [MFMessageComposeViewController canSendText];
    if (!isCanSend) {
        // 提示用户不支持消息发送
        [self alertWithMessage:@"不支持消息发送"];
        return ;
    }
    // 判断是否有接收人
    if (self.recipientArray == nil || self.recipientArray.count == 0) {
        // 提示用户消息不可发送,缺少接收人
        [self alertWithMessage:@"消息不可发送,缺少接收人"];
        return ;
    }
    // 设置代理
    MessageComposeVc.messageComposeDelegate = self ;
    // 设置发送消息的接收者
    MessageComposeVc.recipients = self.recipientArray ;
    // 设置发送的消息内容
    if (self.bodyString) {
        MessageComposeVc.body = self.bodyString ;
    }
    // 判断是否可以设置主题
    BOOL isSetSubject = [MFMessageComposeViewController canSendSubject];
    if (isSetSubject) {
        MessageComposeVc.subject = self.subjectString ;
    }
    // 是否支持添加附件
    BOOL isSendAttachment = [MFMessageComposeViewController canSendAttachments];
    if (isSendAttachment) {
        // 添加附件
        [MessageComposeVc addAttachmentURL:self.attachment.attachmentURl withAlternateFilename:self.attachment.attachmentName];
    }
    // 判断是否支持统一标签的附件
    if (self.uitString && self.uitString.length != 0) {
        BOOL isAttachmentUIT = [MFMessageComposeViewController isSupportedAttachmentUTI:self.uitString];
        if (isAttachmentUIT) {
            [MessageComposeVc addAttachmentData:self.attachment.attachmentData typeIdentifier:self.uitString filename:self.attachment.attachmentName];
        }
    }
    // iMessage 的发送
    if (self.iMessage) {
        MessageComposeVc.message = self.iMessage ;
    }
    // 设置消息页面是否可调用相机
    if (self.isShowUserAttachment) {
        // 调用此方法将禁用视图控制器中的摄像头/附件按钮
        [MessageComposeVc disableUserAttachments];
    }
    // 发送信息
    [TagerController presentViewController:MessageComposeVc animated:YES completion:nil];
    
}

4、短信发送后结果的处理
/*!
 发送信息的事件回调处理函数
 */
- (void)messageComposeViewController:(nonnull MFMessageComposeViewController *)controller didFinishWithResult:(MessageComposeResult)result {
    // 是否返回上一个控制器
    BOOL isCanPush = YES;
    // 事件处理
    switch (result) {
            // 用户取消短信发送
        case MessageComposeResultCancelled:{
            [self alertWithMessage:@"用户取消发送短信"];
        }
            break;
            // 短信发送成功
        case MessageComposeResultSent:{
            [self alertWithMessage:@"短信发送成功,请注意查收"];
        }
            break;
            // 短信发送失败
        case MessageComposeResultFailed:{
            [self alertWithMessage:@"短信发送失败,请重新发送"];
            isCanPush = NO;
        }
            break;
        default:
            break;
    }
    if (!isCanPush) {
        return ;
    }
    // 返回上一个控制器
    [controller dismissViewControllerAnimated:YES completion:nil];
}


第五、SendMessgaeManager 类的测试

1、单一的短信
    SendMessgaeManager * sMessage = [SendMessgaeManager sendMessage:self];

    // 消息内容

    sMessage.bodyString = @"早赤壁帝彩云间,千里江陵一日还";

    // 接收人

    sMessage.recipientArray = @[@"18801210281",@"18401478789"];

    // 调出发送消息的页面

    [sMessage sendMessageMethod];

效果展示如下:
App内发送短信


2、带主题的短信
    SendMessgaeManager * sMessage = [SendMessgaeManager sendMessage:self];

    // 消息内容

    sMessage.bodyString = @"早赤壁帝彩云间,千里江陵一日还";

    // 接收人

    sMessage.recipientArray = @[@"18801210281",@"18401478789"];

    // 主题

    sMessage.subjectString = @"诗词--李白";

    // 调出发送消息的页面

    [sMessage sendMessageMethod];
效果展示如下:
App内发送短信

3、带附件的短信
    SendMessgaeManager * sMessage = [SendMessgaeManager sendMessage:self];

    // 消息内容

    sMessage.bodyString = @"早赤壁帝彩云间,千里江陵一日还";

    // 接收人

    sMessage.recipientArray = @[@"18801210281",@"18401478789"];

    // 主题

    sMessage.subjectString = @"诗词--李白";

    // 附件

    sMessage.attachment.attachmentURl = [NSURL fileURLWithPath:[[NSBundle mainBundle] pathForResource:@"2" ofType:@"png"]];

    sMessage.attachment.attachmentName = @"2.png";

    // 调出发送消息的页面

    [sMessage sendMessageMethod];
效果展示如下:
App内发送短信

4、带统一标示符的短信附件
    SendMessgaeManager * sMessage = [SendMessgaeManager sendMessage:self];

    // 消息内容

    sMessage.bodyString = @"早赤壁帝彩云间,千里江陵一日还";

    // 接收人

    sMessage.recipientArray = @[@"18801210281",@"18401478789"];

    // 主题

    sMessage.subjectString = @"诗词--李白";

    // 设置统一标志符

    sMessage.uitString = @"public.png";

    // 附件(表示符的)

    sMessage.attachment.attachmentName = @"2.png";

    sMessage.attachment.attachmentData = [NSData dataWithContentsOfFile:[[NSBundle mainBundle] pathForResource:@"2" ofType:@"png"]];

    // 调出发送消息的页面

    [sMessage sendMessageMethod];
效果展示如下:
App内发送短信

发送后的结果展示:
App内发送短信