Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

UIPickerView in UITableView

First of all: I know that some people already posted topics like that, but nobody gave a clear answer in all those topics.

I have a settings-UITableView in my application. Now i want to add a TableViewCell where i can choose between some numbers with a UIPickerView.

In the tableView didSelectRowAtIndexPath method i created the if statement for the right cell

-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{

    if (indexPath.row == 1){

    }
}

How can i add a UIPickerView for this cell? It should slide up from the bottom and it would be nice if there is something like a "done" button.

like image 489
Mike_NotGuilty Avatar asked Oct 28 '13 23:10

Mike_NotGuilty


People also ask

Is it possible to add UItableview within a Uitableviewcell?

Implementation of adding a table view inside the cell of UItableview aka, Nested Table View. Used the Power of Autosizing table view and delegate to achieve the expansion and collapse of the cell height.

What is UItableview in Swift?

A view that presents data using rows in a single column. iOS 2.0+ iPadOS 2.0+ Mac Catalyst 13.1+ tvOS 9.0+

What is IndexPath UItableview?

IndexPath contains information about which row in which section the function is asking about. Base on this numbers you are configuring the cell to display the data for given row.

What is IndexPath in Tableview Swift?

indexPath(for:)Returns an index path that represents the row and section of a specified table-view cell.


2 Answers

Have you seen the sample program released with iOS 7 called DateCell? It uses a UIDatePicker, but I found it pretty straightforward to adapt it to a regular UIPickerView.

It does exactly what you're describing: edit a UITableViewCell with a picker that opens directly under the row you're editing.

like image 194
DaiMaoTsai Avatar answered Oct 16 '22 06:10

DaiMaoTsai


This is also based on your other question, so I am including those functionalities here as well (i.e. the switch).

In your YourTableViewController.h

set:

@interface YourTableViewViewController : UITableViewController <UIPickerViewDataSource, UIPickerViewDelegate>

In your YourTableViewController.m

Paste this code:

@interface YourTableViewViewController ()
@property NSInteger toggle;
@property (strong, nonatomic) UIPickerView *pickerView;
@end

@implementation YourTableViewViewController

- (void)viewDidLoad
{
    [super viewDidLoad];
    self.toggle = 0;
    self.pickerView = [[UIPickerView alloc] initWithFrame:(CGRect){{0, 0}, 320, 480}];
    self.pickerView.delegate = self;
    self.pickerView.dataSource = self;
    self.pickerView.center = (CGPoint){160, 640};
    self.pickerView.hidden = YES;
    [self.view addSubview:self.pickerView];
}

#pragma mark - Table view data source

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    // Return the number of rows in the section.
    return 2;    
}

- (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];
        cell.selectionStyle = UITableViewCellSelectionStyleNone;
    }
    if(indexPath.row == 0)
    {
        [cell.contentView addSubview:self.mySwitch];
    }
    if(indexPath.row == 1)
    {
        cell.textLabel.textColor = [UIColor darkGrayColor];
        if(self.toggle == 0)
        {
            cell.textLabel.text = @"Choose a number";
        }
        else
        {
            cell.textLabel.text = @"Cancel";
        }
    }
    // Configure the cell...

    return cell;
}

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
    if(indexPath.row == 1)
    {
        if(self.toggle == 0)
        {
            self.toggle = 1;
            [self.tableView reloadRowsAtIndexPaths:@[indexPath] withRowAnimation:YES];
            [self bringUpPickerViewWithRow:indexPath];
        }
        else
        {
            self.toggle = 0;
            [self.tableView reloadRowsAtIndexPaths:@[indexPath] withRowAnimation:YES];
            [self hidePickerView];
        }
    }
}

- (void)bringUpPickerViewWithRow:(NSIndexPath*)indexPath
{
    UITableViewCell *currentCellSelected = [self.tableView cellForRowAtIndexPath:indexPath];
    [UIView animateWithDuration:1.0f
                          delay:0.0f
                        options:UIViewAnimationOptionCurveEaseInOut
                     animations:^
                     {
                         self.pickerView.hidden = NO;
                         self.pickerView.center = (CGPoint){currentCellSelected.frame.size.width/2, self.tableView.frame.origin.y + currentCellSelected.frame.size.height*4};
                     }
                     completion:nil];
}

- (void)hidePickerView
{
    [UIView animateWithDuration:1.0f
                          delay:0.0f
                        options:UIViewAnimationOptionCurveEaseInOut
                     animations:^
     {
         self.pickerView.center = (CGPoint){160, 800};
     }
                     completion:^(BOOL finished)
     {
         self.pickerView.hidden = YES;
     }];
}

- (void)pickerView:(UIPickerView *)pickerView didSelectRow:(NSInteger)row inComponent:(NSInteger)component
{
    self.toggle = 0;
    [self.tableView reloadData];
    [self hidePickerView];
    NSLog(@"row selected:%ld", (long)row);
}

- (NSString*) pickerView:(UIPickerView *)pickerView titleForRow:(NSInteger)row forComponent:(NSInteger)component
{
    return [NSString stringWithFormat:@"%d", row+1];
}

- (NSInteger)numberOfComponentsInPickerView:(UIPickerView *)pickerView
{
    return 1;
}

- (NSInteger)pickerView:(UIPickerView *)pickerView numberOfRowsInComponent:(NSInteger)component
{
    return 10;
}

@end

Tested.

Addendum:

Also, in your storyboard, change the separator for YourTableView to None (looks better in your case here).

Table View Separator:

in viewDidLoad, add:

self.tableView.separatorStyle = UITableViewCellSeparatorStyleSingleLine;

And in bringUpPickerViewWithRow

after:

UITableViewCell *currentCellSelected = [self.tableView cellForRowAtIndexPath:indexPath];

add:

self.tableView.separatorStyle = UITableViewCellSeparatorStyleNone;
[self.tableView setNeedsDisplay];

And lastly, in hidePickerView, add:

self.tableView.separatorStyle = UITableViewCellSeparatorStyleSingleLine;
[self.tableView setNeedsDisplay];
like image 31
Unheilig Avatar answered Oct 16 '22 07:10

Unheilig