Strange behavior for UITableView after turning from Landscape to Portrait (iPad)

I tried to read the contentOffset of the view table after rotation in the method

willRotateToInterfaceOrientation: Duration :. I created a sample using a UITableViewController with a search bar in tableHeaderView.

Scenario 1: This device is in "Portrait" mode, and I hide the search bar. Then I rotate the device to the landscape. After that, I would expect NOT to see that UISearchbar and contentOffset remain the same.

Scenario 2: This device is in the Landscape, and I hide the search bar. Then I rotate the device to the portrait. After that, I would expect NOT to see the UISearchbar and contentOffset remain the same.

Scenario 1 works as expected. Scenario 2 pulls out the search string and content-content - zero

Does anyone know why ContentOffset matters Zero? I expect this to be 44 (search bar height).

Is there any way to solve this? How do you do this?

// // ViewController.m // test // #import "ViewController.h" @interface ViewController () @end @implementation ViewController - (id)initWithStyle:(UITableViewStyle)style { self = [super initWithStyle:style]; if (self) { // Custom initialization } return self; } - (void)viewDidLoad { [super viewDidLoad]; // Uncomment the following line to preserve selection between presentations. // self.clearsSelectionOnViewWillAppear = NO; // Uncomment the following line to display an Edit button in the navigation bar for this view controller. // self.navigationItem.rightBarButtonItem = self.editButtonItem; } - (void)willRotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration{ //is necessary to prevent showing searchbar dispatch_async(dispatch_get_main_queue(), ^{ double y = self.tableView.contentOffset.y; self.tableView.contentInset = UIEdgeInsetsMake(-1*y, 0, 0, 0); NSLog(@"y %f",y); NSLog(@"Begin offset %@",NSStringFromCGPoint(self.tableView.contentOffset)); }); } - (void)viewDidAppear:(BOOL)animated{ self.tableView.tableHeaderView = [[UISearchBar alloc] initWithFrame:CGRectMake(0, 0, self.tableView.frame.size.width, 44)]; } #pragma mark - Table view data source - (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView { #warning Potentially incomplete method implementation. // Return the number of sections. return 0; } - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section { #warning Incomplete method implementation. // Return the number of rows in the section. return 0; } - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { static NSString *CellIdentifier = @"Cell"; UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; if (cell == nil) { cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier]; } // Configure the cell... return cell; } #pragma mark - Table view delegate - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath { } @end 
+4
source share
2 answers

I think I know where the problem is:

UITableView has a default autoresist mask. Therefore, after turning the device from portrait to landscape, the UITableView becomes smaller (which does not change the offset). If now the user returns to the portrait, the UITableView needs to be stretched and automatically scroll up. To solve this problem, I used a variable to register each "user scroll", for example

  • scrollViewWillBeginDragging (registration)
  • scrollViewDidEndDecelerating (unregistrate)
  • in "scrollViewDidScroll". I check that the scroll comes from the user or not (if the user saves the offset value)

Finally, in the "willRotateToInterfaceOrientation" method, I set the temporary stored offset to a UITableView to keep it in the same position.

Hope there will be a better solution, because my way to solve this problem is a bit more complicated.

+2
source

I have a similar problem that I encountered today and I found a solution for this. An instance variable is declared that supports the contentOffset tableView. Saving the contentOffset value during the - (void) willRotateToInterfaceOrientation: (UIInterfaceOrientation) toInterfaceOrientation duration: (NSTimeInterval) call duration method and applying it to the - (void) viewWillLayoutSubviews method. We must override this method.

 - (void)willRotateToInterfaceOrientation(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration { self.contentOffset = self.tableView.contentOffset; } - (void)viewWillLayoutSubviews { [super viewWillLayoutSubviews]; self.tableView.contentOffset = self.contentOffset; } 

This fixed my problem without any lighting problems.

+1
source

Source: https://habr.com/ru/post/1445024/


All Articles