繁体   English   中英

Objective-C将NSURL传递给另一个ViewController

[英]Objective-C Passing NSURL to another viewcontroller

我有两个视图控制器: FirstViewControllerSecondViewController 该项目是录制视频并将其附加到电子邮件中。 我可以记录下来并可以发送电子邮件,只需要附加它即可。 我可以在FirstViewController获取视频的URL,但是传递它不起作用。

FirstViewController-

- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info 
{

    NSString *mediaType = [info objectForKey:UIImagePickerControllerMediaType];
    if ([mediaType isEqualToString:@"public.movie"])
    {
       // Saving the video to phone / // Get the new unique filename
       NSString *sourcePath = [[info objectForKey:@"UIImagePickerControllerMediaURL"]relativePath];

       UISaveVideoAtPathToSavedPhotosAlbum(sourcePath, self, /*@selector(video:didFinishSavingWithError:contextInfo:)*/nil, nil);
       self.movieURL= [[NSURL alloc] initFileURLWithPath: sourcePath];
       NSLog(@"movieURL");
       NSLog(self.movieURL.absoluteString);

       SecondViewController *sendMovie = [[SecondViewController alloc] initWithNibName:@"ViewController" bundle:nil];
       sendMovie.movieU = [[NSURL alloc] initFileURLWithPath: sourcePath];
       [[self navigationController] pushViewController:sendMovie animated:YES];

       NSLog(@"movieU");
       NSLog(sendMovie.movieU.absoluteString);
   }

   [picker dismissViewControllerAnimated:YES completion:NULL];
}

要附加到电子邮件的SecondViewController-

NSLog(@"1st print");
NSLog(self.movieU);
[controller addAttachmentData:[NSData dataWithContentsOfURL:self.movieU] mimeType:@"video/MOV" fileName:@"defectVideo.MOV"];
NSLog(@"2nd print");
NSLog(self.movieU.absoluteURL);
[self presentViewController:controller animated:YES completion:nil];

NSURL的SecondViewController.h属性

@property(nonatomic) NSURL *movieU; 

movieURL是在一个属性FirstViewController ,但我不认为这是必要的。

我可以看到的URL FirstVC ,但它似乎为零的SecondVC

解决方案 -

1)将NSURL *movieU定义为extern NSURL *movieU而不是属性。

2)否则将其定义为AppDelegate的属性并访问它。

3)否则synthesize属性movieU并像-

在您的FirstViewController中 -

 SecondViewController *sendMovie = [[SecondViewController alloc] initWithNibName:@"ViewController" bundle:nil];
 NSURL *url = [[NSURL alloc] initFileURLWithPath: sourcePath];
 sendMovie.movieU = url;
 [[self navigationController] pushViewController:sendMovie animated:YES];

然后将NSLogSecondViewController中

希望这可以帮助!

您传递信息的方式没有任何问题。 尝试这个:

    // In you code where you create the second view controller.
    SecondViewController *sendMovie = [[SecondViewController alloc] initWithNibName:@"ViewController" bundle:nil];
    // SecondViewController viewDidLoad method being called (movieU is still nil)

    sendMovie.movieU = [[NSURL alloc] initFileURLWithPath: sourcePath]; 

    // Do a nil test here
    if (!sendMovie.movieU) {
        NSLog(@"%@",@"It's nil here!"); // If this is the case something is wrong with "sourcePath"
    } else {
        NSLog(@"%@",@"It's not nil here!");
    }

    [[self navigationController] pushViewController:sendMovie animated:YES];
    // SecondViewController viewWillAppear method being called (movieU is NOT nil)
    // SecondViewController viewDidAppear method being called (movieU is NOT nil)

该测试将告诉您很多。 如果此处为nil,则问题不在于设置第二个视图控制器的属性,而在于实际创建NSURL对象。 可能有很多事情,例如您正在第二个视图控制器中的某个地方覆盖它(例如, viewWillAppear方法)。 只需使用断点,日志记录等方式跟踪路径,即可跟踪其使用寿命。

编辑-调试步骤

在创建Second VC的地方设置断点,设置其属性,推动它,最后查看它(单击选项卡)。 在第二个VC的整个生命周期中设置断点( viewDidLoadviewWillAppearviewDidAppear等)。 这将使您逐步完成VC的整个生命周期。 如果您尚未使用这些方法,请继续定义它们,包括对super的调用。 当您逐步通过这些断点时,请继续检查movieU的值。 您首先会看到它为nil,然后将其设置为nil(从您的评论中知道),而不是nil,然后变为nil,再次等等。如果您有耐心和系统,则可以找到它并学到很多东西关于VC的生命周期。 如果您不系统地完成操作,则可能会错过一些东西。 例如,当您单击选项卡进行实际查看时,您的代码可能正在创建一个全新的Second VC。 以这种方式单步执行代码将显示这一点。

编辑

确保您正在viewWillAppear / viewDidAppear方法或更高版本中进行测试,以便实际上已设置该属性。 查看我的代码中的注释。

编辑

在没有所有权来源的情况下合成的可保留对象指针类型的属性具有其关联实例变量的所有权(如果已存在); 否则,[从Apple 3.1开始,LLVM 3.1开始],其所有权隐含地强大。 在此修订版之前,合成此类属性的格式不正确。

来自: http : //clang.llvm.org/docs/AutomaticReferenceCounting.html#property-declarations

据此(除非您在ivar上指定弱-不太可能),默认情况下它应为强。

祝好运。

用这个

self.movieURL = [NSURL fileURLWithPath:sourcePath];

代替

self.movieURL= [[NSURL alloc] initFileURLWithPath: sourcePath];

希望这项工作

我把它修好了! 我决定使用单例,该单例通过另一个类使用共享实例。 我创建了一个名为Singleton的全新类,只包含了sharedinstance方法:

+ (id)sharedInstance {
static id sharedInstance = nil;
if (sharedInstance == nil) {
    sharedInstance = [[self alloc] init];
}
return sharedInstance;
}

单例

 @property NSURL *movieU;
 + (id)sharedInstance;

确保将单例类导入到First VC和Second VC中。

SecondVC.m

Singleton* single = [Singleton sharedInstance];
[controller addAttachmentData:[NSData dataWithContentsOfURL: single.movieU] mimeType:@"video/MOV" fileName:@"defectVideo.MOV"];

FirstVC.m

Singleton* single = [Singleton sharedInstance];

NSString *mediaType = [info objectForKey:UIImagePickerControllerMediaType];
if ([mediaType isEqualToString:@"public.movie"]){
    // Saving the video / // Get the new unique filename
    NSString *sourcePath = [[info objectForKey:@"UIImagePickerControllerMediaURL"]relativePath];
    UISaveVideoAtPathToSavedPhotosAlbum(sourcePath, self, /*@selector(video:didFinishSavingWithError:contextInfo:)*/nil, nil);
    self.movieURL = [[NSURL alloc] initFileURLWithPath: sourcePath];
    NSLog(@"movieURL");
    single.movieU = self.movieURL;

通过这样做,它成功地将包含要记录的视频信息的URL传递给电子邮件。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM