UITextFieldが押されたときにチェックするtouchesEndedイベントがあります。私がやりたいことは、UIPickerViewを非表示/表示することです。これはどのように行うことができますか?
- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event{
UITouch *touch = [[event allTouches] anyObject];
if (CGRectContainsPoint([self.textField frame], [touch locationInView:self.view]))
{
NSString * error = @"Touched the TextField";
UIAlertView * errorAlert = [[UIAlertView alloc] initWithTitle:@"Selection!" message:error delegate:self cancelButtonTitle:@"OK" otherButtonTitles:nil];
[errorAlert show];
//Want to show or hide UIPickerView
}
}
タッチが発生したときにすでにUIPickerViewが割り当てられています
@interface ThirdViewController : UIViewController <UITextFieldDelegate,UIPickerViewDelegate> {
IBOutlet UIPickerView *pickerView;
}
UIPickerViewはUIViewを継承しているため、「非表示」プロパティを切り替えるだけでよいはずです。
if (pickerView) pickerView.hidden = !pickerView.hidden;
「隠された」プロパティを切り替えるとうまくいきますが、非常に突然の明らかになります。
これを回避する1つの方法は、UIActionSheet内に埋め込むことにより、ピッカーを画面の下から上にスライドさせることです。
次に例を示します。
UIActionSheet *sheet = [[UIActionSheet alloc] initWithTitle:nil
delegate:nil cancelButtonTitle:nil destructiveButtonTitle:nil otherButtonTitles:nil];
CGRect pickerFrame = CGRectMake(0, 0, 0, 0);
UIPickerView *pickerView = [[UIPickerView alloc] initWithFrame:pickerFrame];
pickerView.showsSelectionIndicator = YES;
pickerView.dataSource = self;
pickerView.delegate = self;
[sheet addSubview:pickerView];
[pickerView release];
[sheet showInView:view];
[sheet setBounds:CGRectMake(0, 0, 320, 415)];
self.actionSheet = sheet; // assuming you have setup a property to hold the action sheet
[sheet release];
ピッカーを使い終わったら、それを閉じます。
[self.actionSheet dismissWithClickedButtonIndex:0 animated:YES];
このアプローチを使用して、ピッカーの上のバーにボタンを組み込むこともできます(「完了」、「前へ」、「次へ」など)-方法についての適切な説明があります ここ 。
これらのソリューションがiOS 7で機能しないというコメントを見たので、このスレッドはまだ関連性があり、検索されていると想定します。
これを行うために見つけた最良の方法は、UIPickerViewを(非表示の)UITextFieldに入力ビューとして次のようにアタッチすることです。
_myPicker = [[UIPickerView alloc] init];
_myPicker.delegate = self;
_myPicker.showsSelectionIndicator = YES;
myTextField.inputView = _myPicker;
必要に応じて、テキストフィールドをいつでも非表示にできます。次に、次のように最初のレスポンダーとしてテキストフィールドをアクティブにすることで、UIPickerViewを表示/非表示にできます。
[myTextField becomeFirstResponder];
[myTextField resignFirstResponder];
私はこれがiOS 7で動作することを確認し、iOS 5まで機能しました。
UITextField
の表示/非表示にダミーUIPickerView
を使用しています
最初に、UITextFieldをUIViewController
の@property
として追加します。必要に応じて、UIPickerView
も追加します
@property (strong, nonatomic) UITextField *dummyTextField;
次に、UIPickerView
にinputView
をUITextField
として割り当てます。自分をdataSource
として割り当て、delegate
をUIPickerView
に割り当てます。 UITextField
をUIViewController
のview
のサブビューとして追加する必要があります。
- (void)viewDidLoad {
[super viewDidLoad];
UIPickerView *picker = [[UIPickerView alloc] init];
[picker setDataSource:self];
[picker setDelegate:self];
self.dummyTextField = [UITextField new];
self.dummyTextField.inputView = picker;
[self.dummyTextField setHidden:YES];
[self.view addSubview:self.dummyTextField];
}
最後に、UIPickerView
を表示および非表示にするメカニズムを追加します。私はダミーのUITextField
を使用しているため、「Filter」という名前のUIBarButtonItem
を次のIBAction
とともに追加することにしました。
- (IBAction)tappedFilterButton:(UIBarButtonItem *)sender {
if (self.dummyTextField.isFirstResponder) {
[self.dummyTextField resignFirstResponder];
}
else {
[self.dummyTextField becomeFirstResponder];
}
}
ActionSheetPicker-3.0 を使用できます
UIActionSheet
内のUIPickerViewのように見え、iOS 6-7-8にも採用されています。
だから私はこれを理解しようとする際に多くの参照を使用しました、そして私の最良の参照(それを信じるかどうか)はApple docsから)でした。
UIToolBar、UIToolButton(IBAction "closePicker"付き)、およびUIPickerを保持するメインビューの上にミニビュー( "_pickerView")を作成しました。
*** iOS 4.0以降でのみ機能することに注意してください
uIView( "_pickerView")を閉じて表示するためのコードは次のとおりです。
-(IBAction)closePicker:(id)sender
{
[UIView animateWithDuration:0.3 animations:^{
_pickerView.frame = CGRectMake(_pickerView.frame.Origin.x,
460, //Displays the view off the screen
_pickerView.frame.size.width,
_pickerView.frame.size.height);
}];
}
-(IBAction)showPicker:(id)sender
{
[UIView animateWithDuration:0.3 animations:^{
_pickerView.frame = CGRectMake(_pickerView.frame.Origin.x,
107, //Displays the view a little past the
//center ling of the screen
_pickerView.frame.size.width,
_pickerView.frame.size.height);
}];
}
そして、あなたのviewDidLoadについては、「closePicker」を呼び出すだけで、ロード時にビューが非表示になります
ScrollViewベースのアプリケーションでは、UIPickerViewの表示と非表示はvisible画面の四角形の下部に固定することが比較的難しいため、難しい問題になる可能性があります。次のコードで簡単に行うことができます。
let alertController = UIAlertController(title: title, message: "\n\n\n\n\n\n\n\n\n\n", preferredStyle: .ActionSheet)
alertController.view.addSubview(pickerView)
alertController.addAction(UIAlertAction(title: "OK", style: .Cancel) { action in
})
self.presentViewController(alertController, animated: true, completion: nil)
要約すると、空のメッセージを持つUIAlertControllerを作成します。 alertControllerをpickerViewのサイズにするには、必要な数の改行をメッセージに指定します。そして最後に、pickerViewをalertController.viewのサブビューとして追加します。
次に、選択したpickerView行をUIPickerViewDelegateメソッドで追跡します。
単一のボタン項目を使用してUIPickerViewを非表示および表示(トグル)するためのすっきりした方法を探して、ビットとピースのみを見つけました。同じことをしたい人のために、これが基本的な条件文による私の作業結果です。
ViewController.m
- (IBAction)animatePicker {
if ([self.userSelection.title isEqualToString: (NSString *)@"Select"]) {
_userPicker.hidden = NO;
UIPickerView *pickerView = [[UIPickerView alloc] init]; // default frame is set
float pvHeight = pickerView.frame.size.height;
float y = [[UIScreen mainScreen] bounds].size.height - (pvHeight); // the root view of view controller
[UIView animateWithDuration:0.25f delay:0 options:UIViewAnimationOptionBeginFromCurrentState animations:^{
self.userPicker.frame = CGRectMake(0 , y, pickerView.frame.size.width, pvHeight);
} completion:nil];
} else if ([self.userSelection.title isEqualToString: (NSString *)@"Done"]) {
UIPickerView *pickerView = [[UIPickerView alloc] init]; // default frame is set
float pvHeight = pickerView.frame.size.height;
float y = [[UIScreen mainScreen] bounds].size.height - (pvHeight * -2); // the root view of view controller
[UIView animateWithDuration:0.25f delay:0 options:UIViewAnimationOptionBeginFromCurrentState animations:^{
self.userPicker.frame = CGRectMake(0 , y, pickerView.frame.size.width, pvHeight);
} completion:nil];
self.userSelection.title = @"Select";
}
}
だからここに何が起こっているのですか:「選択」というタイトルの「userSelection」というボタン項目と「userPicker」という非表示のUIPickerViewがあります(非表示にするには、「_ userPicker.hidden」に関するビットをコピーして貼り付けますピッカー宣言で、ブール値をYESに設定します)。ボタン項目は上記のアクションに関連付けられています。ロード時(つまり、ボタンのタイトルに「選択」と表示されている場合)、ピッカーが再表示され、アニメーションで表示されます。 animateWithDurationおよびdelayオプションを使用してその機能を制御できますが、これらの設定は私にはかなり自然に見えます。
次に、このメソッドを使用して、何かが選択されたときにボタンのタイトルを「完了」に変更します。このビットを行うためのより明確な方法があることは確かですが、後でUIを変更する場合に備えて、switchメソッドを使用するとある程度の自由が得られます。
- (void)pickerView:(UIPickerView *)pickerView didSelectRow:(NSInteger)row inComponent:(NSInteger)component{
NSLog(@"Selected Row %ld", (long)row);
switch(row)
{
case 0:
self.userSelection.title = @"Done";
break;
case 1:
self.userSelection.title = @"Done";
break;
case 2:
self.userSelection.title = @"Done";
break;
case 3:
self.userSelection.title = @"Done";
break;
case 4:
self.userSelection.title = @"Done";
break;
case 5:
self.userSelection.title = @"Done";
break;
}
}
最後に、ボタンが「完了」と表示されたときに「else if」でアクションが終了し、逆のアニメーションでピッカーを非表示にし(同じコードですが、「pvHeight * -2」で)、ボタンのタイトルを「」に戻します。アクション全体のループを完了するのに役立つ「選択」。
おそらくそこにいるプロにとってはもっと簡単な方法ですが、私のようにこのようなものに慣れていない人々にとっては、これは最も論理的な意味がありました。さらに、それは機能するので、それは常にボーナスです!
以下は、アニメーションでUIPickerView
を非表示および表示するためのサンプルコードです。
//表示用
-(void)showPickerView{
self.pickerSheet = [UIAlertController alertControllerWithTitle:@"Select font" message:nil preferredStyle:UIAlertControllerStyleActionSheet];
self.pickerView = [[UIPickerView alloc]initWithFrame:CGRectZero];
self.pickerView.dataSource = self;
self.pickerView.delegate = self;
self.pickerView.showsSelectionIndicator = YES;
[self.pickerView selectRow:1 inComponent:0 animated:YES];
[self.pickerSheet.view addSubview:self.pickerView];
self.pickerView.translatesAutoresizingMaskIntoConstraints = NO;
UIView *view = self.pickerView;
[self.pickerSheet.view addConstraints:[NSLayoutConstraint
constraintsWithVisualFormat:@"V:|[view]|"
options:0l
metrics:nil
views:NSDictionaryOfVariableBindings(view)]];
[self.pickerSheet.view addConstraints:[NSLayoutConstraint
constraintsWithVisualFormat:@"H:|[view]|"
options:0l
metrics:nil
views:NSDictionaryOfVariableBindings(view)]];
[self presentViewController:self.pickerSheet animated:YES completion:^{
}];
}
//非表示にする
-(void)hidePickerView{
[self.pickerSheet dismissViewControllerAnimated:YES completion:^{
}];
}