来自xib中自定义TableCell的PresentViewController
Posted
技术标签:
【中文标题】来自xib中自定义TableCell的PresentViewController【英文标题】:PresentViewController from custom TableCell in xib 【发布时间】:2014-04-07 05:21:01 【问题描述】:我创建了自定义 tableView 控制器,在单元格内我放置了一个按钮来打开设备照片库。我的问题,我无法从 CustomCell.m 打开 imagePickerController,它显示以下错误。
请给出一些想法来解决我的问题。
【问题讨论】:
使用委托模式将您的单元格与视图控制器绑定。 你能详细说明你的答案吗? @NeilGaliaskarov 【参考方案1】:TableViewCell 是一个视图,你不能在视图上present
而 UIViewController 可以处理它。您应该将控件从您的单元格转移到包含 tableview 并为其创建自定义单元格的控制器。
试试这样:
自定义单元格.h
类:
@protocol changePictureProtocol <NSObject>
-(void)loadNewScreen:(UIViewController *)controller;
@end
@property (nonatomic, retain) id<changePictureProtocol> delegate;
然后Synthesize it in
.m.
将此添加到m
文件中:
-(IBAction)changePicture:(id)sender
// ..... blah blah
[self.delegate loadNewScreen:picker];
加载此单元格的视图控制器:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
// create cell here
cell.delegate = self;
-(void)loadNewScreen:(UIViewController *)controller;
[self presentViewController:controller animated:YES completion:nil];
它是一个伪代码,可以给你一个想法。
编辑:
Swift 等价物:
CustomTableViewCell.swift
代码:
protocol ChangePictureProtocol : NSObjectProtocol
func loadNewScreen(controller: UIViewController) -> Void;
class CustomTableViewCell: UITableViewCell
// Rest of the class stuff
weak var delegate: ChangePictureProtocol?
@IBAction func changePicture(sender: AnyObject)->Void
var pickerVC = UIImagePickerController();
if((delegate?.respondsToSelector("loadNewScreen:")) != nil)
delegate?.loadNewScreen(pickerVC);
ViewController.swift
代码:
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell
var cell = tableView.dequeueReusableCellWithIdentifier("cellIdentifier") as CustomTableViewCell!
cell.delegate = self;
return cell;
func loadNewScreen(controller: UIViewController)
self.presentViewController(controller, animated: true) () -> Void in
;
【讨论】:
嘿,你介意用 Swift 解释一下吗?从您的解释中将其从 objc 转换时遇到问题。非常感谢。 @lukesIvi,检查我的编辑是否有 swift 等效项,如果您有任何困难,请告诉我。 swift 对我不起作用,我试图显示 print(delegate) 但它只有“nil”这是我的代码: func collectionView(collectionView: UICollectionView, didSelectItemAtIndexPath indexPath: NSIndexPath) print("你好外面") print(delegate) if((delegate?.respondsToSelector("loadNewScreen:")) != nil) print("Hello insinde") let details = MovieDetail();委托?.loadNewScreen(详细信息);打印(委托) @EvanNgo,抱歉回复晚了,刚刚看到你的消息。你设置委托了吗?cell.delegate = self
?
@NeverHopeless 你能帮帮我吗?我明白了,但似乎无法执行【参考方案2】:
提出委托或实例变量的答案是正确的,但是,在大多数情况下,使用特殊的视图控制器来呈现新控制器并不重要。 在这些情况下,以下解决方案要简单得多:只需使用应用程序根视图控制器:
UIViewController* activeVC = [UIApplication sharedApplication].keyWindow.rootViewController;
[activeVC presentViewController:'new view controller'
animated:YES
completion:NULL];
【讨论】:
如果您将表格视图和单元格构造为不在根视图控制器层次结构中,这将不会总是有效“警告:尝试在presentViewController:
消息用于 Viewcontroller。将控件从 Cell 委托给 viewController 并使用同一行将解决您的问题。 UITableViewCell 不响应presentViewController:
消息。
【讨论】:
【参考方案4】:您需要一个UIViewController
来进行演示。您可以在这里做几件事。一种是使用changePicturePressed
回调方法创建自定义委托协议。然后,您可以将包含的视图控制器分配为该委托,并在委托方法中执行演示。
您可以做的另一件事是在初始化期间将UIViewController
传递到您的单元格并将其设置为弱属性。然后,您可以使用该属性直接从单元格内部执行演示。
【讨论】:
【参考方案5】:为您的按钮制作 IBOutlet
然后在cellForRowAtIndexPath
中给按钮指定目标
CustomCell *customCell=[tableView dequeueReusableCellWithIdentifier:@"CellIdentifier"];
[customCell.yourButton addTarget:self action:@selector(yourButtonAction:) forControlEvents:UIControlEventTouchUpInside];
【讨论】:
【参考方案6】:另一种方法是将 CustomCell 的控制器的引用传递给 CustomCell 并使用它来呈现新的控制器。
斯威夫特:
CustomCell.swift
:
class CustomTableViewCell: UITableViewCell
// Rest of the class stuff
var parentViewController: UIViewController? = nil
gotoNewControllerBtn.addTarget(self, action: #selector(gotoNewController), for: .touchUpInside)
func gotoNewController()
let newViewController = NewViewController()
parentViewController.present(newViewController, animated: true, completion: nil)
ViewController.swift
:
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell
var cell = tableView.dequeueReusableCellWithIdentifier("cellIdentifier") as CustomTableViewCell!
cell.parentViewController = self;
return cell;
【讨论】:
【参考方案7】:您需要 viewcontroller 来呈现视图。您不能在 tableviewcells 上显示 viewcontroller。
【讨论】:
以上是关于来自xib中自定义TableCell的PresentViewController的主要内容,如果未能解决你的问题,请参考以下文章
编辑 TableView 时自定义 TableCell 中没有缩进