在一个Uipickerview组件中显示来自两个数组的数据



我正在编写一个程序,该程序用单个组件实现Uipickerview,以从两个阵列(日期和月份)中选择和显示数据。第一个数组包含3行,第二行包含12。程序首先显示带有三个项目的数组。当我选择'Month'按钮以显示第二个数组时,只显示前三个月而不是全部12个。

如果选择'Time-of-Day'按钮,则程序崩溃,指示:

"*** Terminating app due to uncaught exception 'NSRangeException', reason: '*** `-[__NSArrayI objectAtIndex:]: index 3 beyond bounds [0 .. 2]'"`.

我不确定为什么它会超出数组大小。

任何人都可以帮助我了解我需要做的事情:

  1. 更正我的代码以允许选择"月"按钮时显示所有12个月的视图
  2. 在选择'Time-Of-Day'按钮时,请防止程序崩溃,显示一个月后。

以下是代码...

标题

#import <UIKit/UIKit.h>
@interface ViewController : UIViewController <UIPickerViewDataSource, UIPickerViewDelegate>
@property (strong, nonatomic) IBOutlet UITextField *todTxtField;
@property (strong, nonatomic) IBOutlet UITextField *monthTxtField;
@property (strong, nonatomic) NSArray *todArray;
@property (strong, nonatomic) NSArray *monthArray;
@property (strong, nonatomic) IBOutlet UIPickerView *thePickerView;
- (IBAction)monthBtnAction:(id)sender;
- (IBAction)todBtnAction:(id)sender;
@end

实施

#import "ViewController.h"
@interface ViewController () 
@end
@implementation ViewController
@synthesize todArray, monthArray;
@synthesize thePickerView;
@synthesize monthTxtField, todTxtField;
int buttonTouched = 0;
- (void)viewDidLoad
{
    [super viewDidLoad];
    self.todArray = [[NSArray alloc] initWithObjects:@"AM", @"Mid-Day", @"PM", nil];
    self.monthArray =[[NSArray alloc] initWithObjects: @"January", @"February", @"March", @"April",  @"May",  @"June", @"July", @"August", @"September", @"October", @"November", @"December", nil];
}
- (void) viewDidAppear:(BOOL)animated
{
    //set default rows of UITextFields to an initial state
    monthTxtField.text = @"January";
    todTxtField.text = @"Mid-Day";
}
- (void)didReceiveMemoryWarning
{
    [super didReceiveMemoryWarning];
    // Dispose of any resources that can be recreated.
}
#pragma mark Button Actions
- (IBAction)todBtnAction:(id)sender
{
    buttonTouched = 0;
    [thePickerView reloadAllComponents];
}
- (IBAction)monthBtnAction:(id)sender
{
    buttonTouched = 1;
    [thePickerView reloadAllComponents];
}
#pragma mark Picker
// returns the number of components to be used
- (NSInteger)numberOfComponentsInPickerView:(UIPickerView *)pickerView
{
    return 1;
}

// returns the # of rows in the components
- (NSInteger)pickerView:(UIPickerView *)pickerView numberOfRowsInComponent:NSInteger)component
{
    switch (buttonTouched)
    {
        case 0:
            return [todArray count];
            break;
        default:
            return [monthArray count];
            break;
    }
}
//Display the row number from the array
- (NSString *)pickerView:(UIPickerView *)pickerView titleForRow:(NSInteger)row forComponent:(NSInteger)component
{
    switch (buttonTouched)
    {
        case 0:
            return [todArray objectAtIndex:row];
            break;
        default:
            return [monthArray objectAtIndex:row];
            break;
     }
}
//Display the row content from the array
- (void)pickerView:(UIPickerView *)pickerView didSelectRow:(NSInteger)row inComponent:(NSInteger)component
{
    switch (buttonTouched)
    {
        case 0:
           self.todTxtField.text = [todArray objectAtIndex:row];
           break;
        default:
           self.monthTxtField.text = [monthArray objectAtIndex:row];
           break;
     }
}
@end

如果在组件0中的当前选择的行大于2时,当您翻转组件0以表示带有3个成员的数组,而不是带有12个成员的数组,则肯定会崩溃。因此,在您从一个月阵列翻转到AM/PM之前,您需要致电

[picker selectRow:0 inComponent:0 animated:YES]

否则,采摘者将尝试选择12月的第11行,例如每次都只有三个,范围异常...

编辑..摘要.. uipickerview具有您尚未考虑的变量,每个组件中当前选择的行。重新加载数据不会改变此变量,您需要稍微照顾它。