Ios 从UIViewController返回到tableViewController时出现白色框
回到tableViewController时,我意识到视图控制器旁边有一个白色框。如果我有任何框架或子视图或类似的东西,我会检查我的代码 下面是显示我的问题的gif: 下面是我的MasterViewController.h和.m(即tableview)的内容 MasterViewController.hIos 从UIViewController返回到tableViewController时出现白色框,ios,objective-c,uiviewcontroller,uitableview,Ios,Objective C,Uiviewcontroller,Uitableview,回到tableViewController时,我意识到视图控制器旁边有一个白色框。如果我有任何框架或子视图或类似的东西,我会检查我的代码 下面是显示我的问题的gif: 下面是我的MasterViewController.h和.m(即tableview)的内容 MasterViewController.h #import <UIKit/UIKit.h> #import <CoreData/CoreData.h> @interface XMMasterViewContro
#import <UIKit/UIKit.h>
#import <CoreData/CoreData.h>
@interface XMMasterViewController : UITableViewController <NSFetchedResultsControllerDelegate>
@property (strong, nonatomic) NSFetchedResultsController *fetchedResultsController;
@property (strong, nonatomic) NSManagedObjectContext *managedObjectContext;
@end
#import <UIKit/UIKit.h>
@interface XMDetailViewController : UIViewController {
// IBOutlet UISwitch *switchButton;
}
@property (strong, nonatomic) id detailItem;
@property (weak, nonatomic) IBOutlet UILabel *titleLabel;
@property (weak, nonatomic) IBOutlet UILabel *locationLabel;
@property (weak, nonatomic) IBOutlet UILabel *timeLabel;
@property (weak, nonatomic) IBOutlet UITextView *todoTextView;
@property (weak, nonatomic) IBOutlet UIView *selectionView;
- (IBAction)todoDoneTouched:(UIButton *)sender;
- (IBAction)shareTouched:(id)sender;
@end
#导入
#进口
@接口XMMasterViewController:UITableViewController
@属性(强,非原子)NSFetchedResultsController*fetchedResultsController;
@属性(强,非原子)NSManagedObjectContext*managedObjectContext;
@结束
MasterViewController.m
#import "XMMasterViewController.h"
#import "XMDetailViewController.h"
#import "XMEditViewController.h"
@interface XMMasterViewController ()
@property (nonatomic, strong) XMDetailViewController *detailViewController;
- (void)configureCell:(UITableViewCell *)cell atIndexPath:(NSIndexPath *)indexPath;
- (void)dataChangedFromICloud:(NSNotification*)note;
@end
@implementation XMMasterViewController
- (void)awakeFromNib
{
if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPad) {
self.clearsSelectionOnViewWillAppear = NO;
self.preferredContentSize = CGSizeMake(320.0, 600.0);
}
[super awakeFromNib];
}
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
self.navigationItem.leftBarButtonItem = self.editButtonItem;
UIBarButtonItem *addButton = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemAdd target:self action:@selector(insertNewObject:)];
self.navigationItem.rightBarButtonItem = addButton;
self.detailViewController = (XMDetailViewController *)[[self.splitViewController.viewControllers lastObject] topViewController];
dispatch_async(dispatch_get_main_queue(), ^{
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(dataChangedFromICloud:) name:@"databaseChanged" object:nil];
});
[self.tableView reloadData];
}
- (void)viewDidUnload
{
[[NSNotificationCenter defaultCenter] removeObserver:self];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
- (void)insertNewObject:(id)sender
{
NSManagedObjectContext *context = [self.fetchedResultsController managedObjectContext];
NSEntityDescription *entity = [[self.fetchedResultsController fetchRequest] entity];
NSManagedObject *newManagedObject = [NSEntityDescription insertNewObjectForEntityForName:[entity name] inManagedObjectContext:context];
// If appropriate, configure the new managed object.
// Normally you should use accessor methods, but using KVC here avoids the need to add a custom class to the template.
[newManagedObject setValue: NSLocalizedString(@"name", nil) forKey:@"title"];
[newManagedObject setValue:[NSDate date] forKey:@"timestamp"];
[newManagedObject setValue:[NSDate date] forKey:@"creationDate"];
[newManagedObject setValue: nil forKey:@"text"];
[newManagedObject setValue: NSLocalizedString(@"place", nil) forKey:@"location"];
// Save the context.
NSError *error = nil;
if (![context save:&error]) {
// Replace this implementation with code to handle the error appropriately.
// abort() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development.
NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
abort();
}
[self performSegueWithIdentifier:@"addSegue" sender:newManagedObject];
}
#pragma mark - Table View
/*- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
NSArray *array = [[NSArray alloc] initWithObjects:@"Noch zu erledigen",@"Erledigt",nil];
return array.count;
}*/
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
return [[self.fetchedResultsController sections] count];
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
id <NSFetchedResultsSectionInfo> sectionInfo = [self.fetchedResultsController sections][section];
return [sectionInfo numberOfObjects];
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"Cell" forIndexPath:indexPath];
[self configureCell:cell atIndexPath:indexPath];
return cell;
}
- (BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath
{
// Return NO if you do not want the specified item to be editable.
return YES;
}
- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
if (editingStyle == UITableViewCellEditingStyleDelete) {
NSManagedObjectContext *context = [self.fetchedResultsController managedObjectContext];
[context deleteObject:[self.fetchedResultsController objectAtIndexPath:indexPath]];
NSError *error = nil;
if (![context save:&error]) {
// Replace this implementation with code to handle the error appropriately.
// abort() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development.
NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
abort();
}
}
}
- (BOOL)tableView:(UITableView *)tableView canMoveRowAtIndexPath:(NSIndexPath *)indexPath
{
// The table view should not be re-orderable.
return NO;
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPad) {
NSManagedObject *object = [[self fetchedResultsController] objectAtIndexPath:indexPath];
self.detailViewController.detailItem = object;
self.detailViewController.selectionView.hidden = YES;
}
}
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
if ([[segue identifier] isEqualToString:@"showDetail"]) {
NSIndexPath *indexPath = [self.tableView indexPathForSelectedRow];
NSManagedObject *object = [[self fetchedResultsController] objectAtIndexPath:indexPath];
[[segue destinationViewController] setDetailItem:object];
} else if ([segue.identifier isEqualToString:@"addSegue"]) {
XMEditViewController *editVC = segue.destinationViewController;
editVC.detailItem = sender;
}
}
#pragma mark - Fetched results controller
- (NSFetchedResultsController *)fetchedResultsController
{
if (_fetchedResultsController != nil) {
return _fetchedResultsController;
}
NSManagedObjectContext* context = [self managedObjectContext];
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
// Edit the entity name as appropriate.
NSEntityDescription* entity = [NSEntityDescription entityForName:@"Todo" inManagedObjectContext:context];
[fetchRequest setEntity:entity];
// Set the batch size to a suitable number.
[fetchRequest setFetchBatchSize:20];
// Edit the sort key as appropriate.
NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"timestamp" ascending:YES];
NSArray *sortDescriptors = @[sortDescriptor];
[fetchRequest setSortDescriptors:sortDescriptors];
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"done == %@", @(NO)];
[fetchRequest setPredicate:predicate];
// Edit the section name key path and cache name if appropriate.
// nil for section name key path means "no sections".
NSFetchedResultsController *aFetchedResultsController = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest managedObjectContext:self.managedObjectContext sectionNameKeyPath:@"done" cacheName:nil];
aFetchedResultsController.delegate = self;
self.fetchedResultsController = aFetchedResultsController;
NSError *error = nil;
if (![self.fetchedResultsController performFetch:&error]) {
// Replace this implementation with code to handle the error appropriately.
// abort() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development.
NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
abort();
}
return _fetchedResultsController;
}
- (void)controllerWillChangeContent:(NSFetchedResultsController *)controller
{
[self.tableView beginUpdates];
}
- (void)controller:(NSFetchedResultsController *)controller didChangeSection:(id <NSFetchedResultsSectionInfo>)sectionInfo
atIndex:(NSUInteger)sectionIndex forChangeType:(NSFetchedResultsChangeType)type
{
switch(type) {
case NSFetchedResultsChangeInsert:
[self.tableView insertSections:[NSIndexSet indexSetWithIndex:sectionIndex] withRowAnimation:UITableViewRowAnimationFade];
break;
case NSFetchedResultsChangeDelete:
[self.tableView deleteSections:[NSIndexSet indexSetWithIndex:sectionIndex] withRowAnimation:UITableViewRowAnimationFade];
break;
}
}
- (void)controller:(NSFetchedResultsController *)controller didChangeObject:(id)anObject
atIndexPath:(NSIndexPath *)indexPath forChangeType:(NSFetchedResultsChangeType)type
newIndexPath:(NSIndexPath *)newIndexPath
{
UITableView *tableView = self.tableView;
switch(type) {
case NSFetchedResultsChangeInsert:
[tableView insertRowsAtIndexPaths:@[newIndexPath] withRowAnimation:UITableViewRowAnimationFade];
break;
case NSFetchedResultsChangeDelete:
[tableView deleteRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationFade];
break;
case NSFetchedResultsChangeUpdate:
[self configureCell:[tableView cellForRowAtIndexPath:indexPath] atIndexPath:indexPath];
break;
case NSFetchedResultsChangeMove:
[tableView deleteRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationFade];
[tableView insertRowsAtIndexPaths:@[newIndexPath] withRowAnimation:UITableViewRowAnimationFade];
break;
}
}
- (void)controllerDidChangeContent:(NSFetchedResultsController *)controller
{
[self.tableView reloadData];
[self.tableView endUpdates];
}
- (void)configureCell:(UITableViewCell *)cell atIndexPath:(NSIndexPath *)indexPath
{
NSManagedObject *object = [self.fetchedResultsController objectAtIndexPath:indexPath];
cell.textLabel.text = [object valueForKey:@"title"];
cell.detailTextLabel.text = @"Test";
NSDate *date = [object valueForKey:@"timestamp"];
NSDateFormatter *format = [[NSDateFormatter alloc] init];
[format setDateFormat:@"dd.MM.yyyy"];
NSDate *time = [object valueForKey:@"timestamp"];
NSDateFormatter *timeformat = [NSDateFormatter new];
[timeformat setDateFormat:@"HH:mm"];
cell.detailTextLabel.text = [NSString stringWithFormat:NSLocalizedString(@"display",nil), [format stringFromDate:date], [timeformat stringFromDate:time]];
}
#pragma mark - iCloud refresh
- (void)dataChangedFromICloud:(NSNotification*)note
{
dispatch_async(dispatch_get_main_queue(), ^{
NSError *error = nil;
if(self.fetchedResultsController) {
if([self.fetchedResultsController performFetch:&error]) {
NSLog(@"Error! %@ %@", error, [error userInfo]);
}
[self.tableView reloadData];
}
});
}
@end
#import "XMDetailViewController.h"
#import "XMEditViewController.h"
#import "XMInfoViewController.h"
#import <Social/Social.h>
@interface XMDetailViewController ()
@property (strong, nonatomic) UIPopoverController *masterPopoverController;
- (void)configureView;
@end
@implementation XMDetailViewController
#pragma mark - Managing the detail item
- (void)setDetailItem:(id)newDetailItem
{
if (_detailItem != newDetailItem) {
_detailItem = newDetailItem;
// Update the view.
[self configureView];
}
if (self.masterPopoverController != nil) {
[self.masterPopoverController dismissPopoverAnimated:YES];
}
}
- (void)configureView
{
// Update the user interface for the detail item.
if (self.detailItem) {
self.titleLabel.text = [self.detailItem valueForKey:@"title"];
self.todoTextView.text = [self.detailItem valueForKey:@"text"];
self.locationLabel.text = [self.detailItem valueForKey:@"location"];
NSDate *date = [self.detailItem valueForKey:@"timestamp"];
NSDateFormatter *format = [NSDateFormatter new];
[format setDateFormat:@"dd.MM.yyyy"];
NSDate *time = [self.detailItem valueForKey:@"timestamp"];
NSDateFormatter *timeformat = [NSDateFormatter new];
[timeformat setDateFormat:@"HH:mm"];
self.timeLabel.text = [NSString stringWithFormat:NSLocalizedString(@"display",nil), [format stringFromDate:date], [timeformat stringFromDate:time]];
}
}
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
// switchButton.on = [[self.detailItem valueForKey:@"done"] boolValue];
}
- (void)viewWillAppear:(BOOL)animated
{
[self configureView];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
- (IBAction)todoDoneTouched:(UIButton *)sender {
[self.detailItem setValue:@(YES) forKey:@"done"];
NSManagedObjectContext *context = [self.detailItem managedObjectContext];
NSError *error = nil;
if(![context save:&error]) {
NSLog(NSLocalizedString(@"error1",nil), error, [error userInfo]);
abort();
}
if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPad) {
self.selectionView.hidden = NO;
}
[self.navigationController popViewControllerAnimated:YES];
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"myTodo" message:NSLocalizedString(@"done2",nil) delegate:nil cancelButtonTitle:@"Okay" otherButtonTitles:nil, nil];
[alert show];
NSLog(NSLocalizedString(@"done1",nil));
}
/*-(IBAction)theSwitch {
if (switchButton.on) {
[self.detailItem setValue:@(YES) forKey:@"done"];
NSManagedObjectContext *context = [self.detailItem managedObjectContext];
NSError *error = nil;
if(![context save:&error]) {
NSLog(NSLocalizedString(@"error1",nil), error, [error userInfo]);
abort();
}
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"myTodo" message:NSLocalizedString(@"done2",nil) delegate:nil cancelButtonTitle:@"Okay" otherButtonTitles:nil, nil];
[alert show];
NSLog(NSLocalizedString(@"done1",nil));
} else {
[self.detailItem setValue:@(NO) forKey:@"done"];
NSManagedObjectContext *context = [self.detailItem managedObjectContext];
NSError *error = nil;
if(![context save:&error]) {
NSLog(NSLocalizedString(@"error1",nil), error, [error userInfo]);
abort();
}
}
}
*/
- (IBAction)shareTouched:(id)sender {
NSString *titleString = [self.detailItem valueForKey:@"title"];
NSDate *date = [self.detailItem valueForKey:@"timestamp"];
NSDateFormatter *format = [NSDateFormatter new];
[format setDateFormat:@"dd.MM.yyyy"];
NSDate *time = [self.detailItem valueForKey:@"timestamp"];
NSDateFormatter *timeformat = [NSDateFormatter new];
[timeformat setDateFormat:@"HH:mm"];
NSString *initialString = [NSString stringWithFormat:NSLocalizedString(@"post",nil), titleString, [format stringFromDate:date], [timeformat stringFromDate:time]];
NSURL *url = [NSURL URLWithString:@"http://s.xnmn.de/mytodo"];
UIImage *image = [UIImage imageNamed:@"AppIcon76x76@2x"];
NSArray *activityItems = [NSArray arrayWithObjects:initialString, image, url, nil];
UIActivityViewController *activityViewController = [[UIActivityViewController alloc] initWithActivityItems:activityItems applicationActivities:nil];
activityViewController.modalTransitionStyle = UIModalTransitionStyleCoverVertical;
activityViewController.excludedActivityTypes = @[UIActivityTypePrint, UIActivityTypeCopyToPasteboard, UIActivityTypeAssignToContact, UIActivityTypeSaveToCameraRoll, UIActivityTypeAddToReadingList];
[self presentViewController:activityViewController animated:YES completion:nil];
}
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
if([segue.identifier isEqualToString:@"editSegue"]){
XMEditViewController *editVC = segue.destinationViewController;
editVC.detailItem = self.detailItem;
}
}
- (void)splitViewController:(UISplitViewController *)splitController willHideViewController:(UIViewController *)viewController withBarButtonItem:(UIBarButtonItem *)barButtonItem forPopoverController:(UIPopoverController *)popoverController
{
barButtonItem.title = NSLocalizedString(@"Master",nil);
[self.navigationItem setLeftBarButtonItem:barButtonItem animated:YES];
self.masterPopoverController = popoverController;
}
- (void)splitViewController:(UISplitViewController *)splitController willShowViewController:(UIViewController *)viewController invalidatingBarButtonItem:(UIBarButtonItem *)barButtonItem
{
// Called when the view is shown again in the split view, invalidating the button and popover controller.
[self.navigationItem setLeftBarButtonItem:nil animated:YES];
self.masterPopoverController = nil;
}
@end
#导入“XMMasterViewController.h”
#导入“XMDetailViewController.h”
#导入“XMEditViewController.h”
@接口XMMasterViewController()
@属性(非原子,强)XMDetailViewController*detailViewController;
-(void)configureCell:(UITableViewCell*)单元格atIndexPath:(NSIndexPath*)indexPath;
-(作废)来自云的数据更改:(NSNotification*)注释;
@结束
@MasterViewController的实现
-(无效)从NIB中唤醒
{
if([[UIDevice currentDevice]userInterfaceIdiom]==UIUserInterfaceIdiomPad){
self.clearselectiononviewwillappear=否;
self.preferredContentSize=CGSizeMake(320.0600.0);
}
[超级awakeFromNib];
}
-(无效)viewDidLoad
{
[超级视图下载];
//加载视图后,通常从nib执行任何其他设置。
self.navigationItem.leftBarButtonItem=self.editButtonItem;
UIBarButtonItem*addButton=[[UIBarButtonItem alloc]initWithBarButtonSystemItem:UIBarButtonSystemItemAddTarget:self action:@selector(insertNewObject:)];
self.navigationItem.rightBarButtonItem=addButton;
self.detailViewController=(XMDetailViewController*)[[self.splitViewController.viewControllers lastObject]topViewController];
dispatch\u async(dispatch\u get\u main\u queue()^{
[[NSNotificationCenter defaultCenter]添加观察者:自选择器:@selector(DataChangedFromicCloud:)名称:@“databaseChanged”对象:nil];
});
[self.tableView重载数据];
}
-(无效)视图卸载
{
[[NSNotificationCenter defaultCenter]移除观察者:self];
}
-(无效)未收到记忆警告
{
[超级记忆警告];
//处置所有可以重新创建的资源。
}
-(void)insertNewObject:(id)发送方
{
NSManagedObjectContext*上下文=[self.fetchedResultsController managedObjectContext];
NSEntityDescription*实体=[[self.fetchedResultsController fetchRequest]实体];
NSManagedObject*newManagedObject=[NSEntityDescription insertNewObjectForEntityForName:[实体名称]在ManagedObjectContext:context]中;
//如果合适,请配置新的托管对象。
//通常您应该使用访问器方法,但是在这里使用KVC可以避免向模板添加自定义类。
[newManagedObject设置值:NSLocalizedString(@“name”,nil)forKey:@“title”];
[newManagedObject setValue:[NSDate date]forKey:@“时间戳”];
[newManagedObject setValue:[NSDate date]forKey:@“creationDate”];
[newManagedObject设置值:nil forKey:@“text”];
[newManagedObject设置值:NSLocalizedString(@“place”,nil)forKey:@“location”];
//保存上下文。
n错误*错误=nil;
如果(![上下文保存:&错误]){
//将此实现替换为适当处理错误的代码。
//abort()导致应用程序生成崩溃日志并终止。您不应该在装运应用程序中使用此函数,尽管它在开发过程中可能很有用。
NSLog(@“未解决的错误%@,%@”,错误,[error userInfo]);
中止();
}
[self-PerformsgueWithIdentifier:@“addSegue”发件人:newManagedObject];
}
#pragma标记-表视图
/*-(NSInteger)表格视图中的节数:(UITableView*)表格视图{
NSArray*数组=[[NSArray alloc]initWithObjects:@“Noch zu erledigen”,“Erledigt”,nil];
返回array.count;
}*/
-(NSInteger)表格视图中的节数:(UITableView*)表格视图
{
返回[[self.fetchedResultsController节]计数];
}
-(NSInteger)表视图:(UITableView*)表视图行数节:(NSInteger)节
{
id sectionInfo=[self.fetchedResultsController sections][section];
返回[sectionInfo numberOfObjects];
}
-(UITableViewCell*)tableView:(UITableView*)tableView cellForRowAtIndexPath:(NSIndexPath*)indexPath
{
UITableViewCell*cell=[tableView dequeueReusableCellWithIdentifier:@“cell”forIndexPath:indexPath];
[self-configureCell:cell-atIndexPath:indexPath];
返回单元;
}
-(BOOL)tableView:(UITableView*)tableView caneditrowatinexpath:(nsindepath*)indepath
{
//如果不希望指定的项可编辑,则返回“否”。
返回YES;
}
-(void)tableView:(UITableView*)tableView提交的编辑样式:(UITableViewCellEditingStyle)行的编辑样式索引路径:(NSIndexPath*)索引路径
{
如果(editingStyle==UITableViewCellEditingStyleDelete){
NSManagedObjectContext*上下文=[self.fetchedResultsController managedObjectContext];
[上下文删除对象:[self.fetchedResultsController对象索引路径:indexPath]];
n错误*错误=nil;
如果(![上下文保存:&错误]){
//将此实现替换为适当处理错误的代码。
//abort()导致应用程序生成崩溃日志并终止。您不应该在装运应用程序中使用此函数,尽管它在开发过程中可能很有用。
NSLog(@“未解决的错误%@,%@”,错误,[error userInfo]);
中止();
}
}
}
-(BOOL)tableView:(UITableView*)tableView可以移动rowatinexpath:(nsindepath*)indepath
{
//表视图不应可重新排序。
返回否;
}
-(void)tableView:(UITableView*)tableView未选择RowatineXpath:(NSIndexPath*)indexPath
{
if([[UIDevice currentDevice]userInterfaceIdiom]==UIUserInterfaceIdiomPad){