Ios 如何使用UIPasteboard for animated.gif异步加载图像URL

Ios 如何使用UIPasteboard for animated.gif异步加载图像URL,ios,objective-c,iphone-5,Ios,Objective C,Iphone 5,我的视图上有一个UIButton,下面是我按下该按钮时的代码 - (IBAction)sendSMS:(UIButton *)sender { NSData *gifImage = [[NSData alloc] initWithContentsOfURL:url]; UIPasteboard *pasteBoard = [UIPasteboard generalPasteboard]; pasteBoard.persistent = YES; //paste

我的视图上有一个UIButton,下面是我按下该按钮时的代码

- (IBAction)sendSMS:(UIButton *)sender 
{
    NSData *gifImage = [[NSData alloc] initWithContentsOfURL:url];

    UIPasteboard *pasteBoard = [UIPasteboard generalPasteboard];
    pasteBoard.persistent = YES;
    //pasteBoard.image = self.messageViewImage;
    [pasteBoard setData:gifImage forPasteboardType:@"com.compuserve.gif"];

    NSString *phoneToCall = @"sms:";
    NSString *phoneToCallEncoded = [phoneToCall     stringByAddingPercentEscapesUsingEncoding:NSASCIIStringEncoding];
    NSURL *url = [[NSURL alloc] initWithString:phoneToCallEncoded];
    [[UIApplication sharedApplication] openURL:url];
}

我正在尝试复制要粘贴到彩信中的动画gif。如何异步完成此任务?当前当我按下按钮时,大约需要3秒钟,按钮背景为蓝色,然后会弹出彩信。我如何才能让这对用户来说是一种更好的体验?

我不知道这是否会有帮助,因为加载映像所需的时间不会因为您异步执行而缩短。但这里是如何异步完成的

dispatch_queue_t que = dispatch_queue_create("myque", DISPATCH_QUEUE_SERIAL);
dispatch_async(que, ^{

    NSData *gifImage = [[NSData alloc] initWithContentsOfURL:url];

    dispatch_async(dispatch_get_main_queue(), ^{

        UIPasteboard *pasteBoard = [UIPasteboard generalPasteboard];
        pasteBoard.persistent = YES;
        //pasteBoard.image = self.messageViewImage;
        [pasteBoard setData:gifImage forPasteboardType:@"com.compuserve.gif"];

    });
});

NSString *phoneToCall = @"sms:";
NSString *phoneToCallEncoded = [phoneToCall stringByAddingPercentEscapesUsingEncoding:NSASCIIStringEncoding];
NSURL *url = [[NSURL alloc] initWithString:phoneToCallEncoded];
[[UIApplication sharedApplication] openURL:url];

这里重要的一点是,您要记住在主界面上更新GUI的所有代码,否则GUI将不会更新。

实现目标的一种方法是使用
MessageUI
框架显示
MFMessageComposeViewController
,并将GIF作为附件添加。使用这种方法,您永远不必将用户切换到Messages应用程序—所有操作都在您自己的应用程序中完成。下面是你如何做到这一点

第一步是向项目中添加以下框架:

  • MessageUI.framework
  • MobileCoreServices.framework
在视图控制器中,添加以下导入:

#import <MessageUI/MessageUI.h>
#import <MobileCoreServices/UTCoreTypes.h>
我们正在定义一个属性,以便稍后在MMS视图中处理用户点击
Cancel

在视图控制器的
viewDidLoad
中,添加以下内容:

self.messageController = [[MFMessageComposeViewController alloc] init];
self.messageController.messageComposeDelegate = self;
您希望您的
sendSMS
方法如下所示:

- (IBAction)sendSMS:(UIButton *)sender 
{
    [UIApplication sharedApplication].networkActivityIndicatorVisible = YES;

    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0), ^{
        NSData *gifData = [NSData dataWithContentsOfURL:[NSURL URLWithString:url]];

        if ([MFMessageComposeViewController canSendText]) {
            [self.messageController addAttachmentData:gifData typeIdentifier:(__bridge NSString *)kUTTypeGIF filename:@"animated.gif"];

            dispatch_async(dispatch_get_main_queue(), ^{
                [self presentViewController: self.messageController animated:YES completion:NULL];
            });
        }

        [UIApplication sharedApplication].networkActivityIndicatorVisible = NO;
    });
}
在此方法中,GIF在后台下载并分配给
gifData
<代码>gifData随后作为附件添加到消息生成器视图中,并向用户显示生成器视图

当用户发送彩信或点击
取消
按钮时,将调用
消息composeviewcontroller:didfishwithresult:
。在该方法中,您需要关闭message composer模式视图:

- (void)messageComposeViewController:(MFMessageComposeViewController *)controller didFinishWithResult:(MessageComposeResult)result
{
    [self.smsComposer dismissViewControllerAnimated:YES completion:NULL];
}

result
参数将是
messagecomposesultcancelled
messagecomposesultsent
messagecomposesultfailed
,具体取决于用户所做的操作

注意双重运行'-(iAction)sendSMS:(UIButton*)sender',因为代码不是线程/逻辑保存。如果你运行两次,你会看到两个对话框一个接一个。如果是重量级gif图像,用户点击两次很容易发生这种情况
- (void)messageComposeViewController:(MFMessageComposeViewController *)controller didFinishWithResult:(MessageComposeResult)result
{
    [self.smsComposer dismissViewControllerAnimated:YES completion:NULL];
}