3

分割ビューテンプレートを使用して、もちろんポートレートモードのポップオーバーを持つ単純な分割ビューを作成しています。テンプレートによって生成されたデフォルトのコードを使用しています。このコードは、ツールバーアイテムを追加/削除し、ポップオーバーコントローラーを設定して削除します。これらの2つのメソッドは、splitViewController:willShowViewController:...とsplitViewController:willHideViewController:...です。

ポップオーバーが表示されているときにユーザーがツールバーボタンをタップした場合にポップオーバーが消える方法を見つけようとしています。ポップオーバーの外側をタップすると、アイテムを選択せず​​にポップオーバーを非表示にすることができますが、ユーザーがもう一度ボタンをタップすると、ポップオーバーを非表示にしたいと思います。

私が立ち往生しているのはこれです:ツールバーボタンのアクションにフックするための明白で簡単な方法はないようです。デバッガーを使用すると、ボタンで呼び出されているアクションがshowMasterInPopoverであることがわかります。そして、私はプログラムでセレクターを操作するのは初めてです、と私は認めます。

どういうわけか、すでに存在するアクションをオーバーライドせずに、アクションを記述してツールバー項目に設定できますか?たとえば、現在あるアクションを呼び出すアクションを追加しますか?または、ポップオーバーを自分で表示/非表示にするアクションを作成する必要があります(おそらく現在スプリットビューコントローラーによって舞台裏で行われている動作???)。

または、設定されている既存の動作を変更せずに、この動作をこのボタンに追加する簡単な方法がありませんか?

ありがとうございました!

4

6 に答える 6

6

したがって、次のようにSplitViewController willPresentViewControllerメソッドを実装することで、barButtonItemをクリックしたときにポップオーバーを閉じることができることがわかります。

- (void) splitViewController:(UISplitViewController *)svc 
           popoverController: (UIPopoverController *)pc
   willPresentViewController: (UIViewController *)aViewController
{
    if (pc != nil) {
        [pc dismissPopoverAnimated:YES];
    }
}
于 2010-04-23T21:44:58.220 に答える
1

したがって、barButtonItemには、ターゲットとしてUISplitViewControllerがあり、アクションとしてshowMasterInPopover:があります。ドキュメントに見つからないので、呼び出すのがうまくいかないのではないかと少し心配していますが、ターゲットを自分自身(ビューコントローラー)に変更し、アクションをカスタムメソッドに変更することで機能するようになりました。これ:

- (void)showMasterInPopover:(id)sender {
    // ...insert custom stuff here...
    [splitViewController showMasterInPopover:sender];
}
于 2010-04-14T20:44:40.650 に答える
0

実際のコメントをする担当者がいません。:-(

@Jann-エリザベスがやりたいことはかなり標準的だと確信しています。たとえば、iPadにプリロードされた状態で出荷されるNotesアプリケーションは、左上隅のツールバーボタンを押すとポップオーバーを閉じて開きます。

于 2010-04-17T15:28:09.137 に答える
0

以下は私の解決策です。UISplitViewControllerツールバーボタンのイベントハンドラーをフックすることにより、greenisusのソリューションと同様に開始します。コントローラーのフラグを使用して、ポップオーバーが開いているかどうかを追跡します。最後に、ユーザーがポップオーバーを開いてから、ポップオーバーの外側をクリックして閉じる場合を処理するために、UIPopoverControllerDelegateプロトコルを実装します。

まず、コントローラーインターフェイス:

@interface LaunchScene : NSObject <UISplitViewControllerDelegate, UIPopoverControllerDelegate>
{
    UISplitViewController* _splitViewController;    //Shows list UITableView on the left, and details on the right
    UIToolbar* _toolbar;                            //Toolbar for the button that will show the popover, when in portrait orientation
    SEL _svcAction;                                 //The action from the toolbar
    id _svcTarget;                                  //The target object from the toolbar
    UIPopoverController* _popover;                  //The popover that might need to be dismissed
    BOOL _popoverShowing;                           //Whether the popover is currently showing or not
}

-(void) svcToolbarClicked: (id)sender;

私は_svcActionと_svcTargetを使用して、彼が正しい関数を呼び出していない可能性があるというgreenisusの心配を追加します。

以下は私の実装です。簡潔にするために、UISplitViewControllerとサブビューをインスタンス化するコードは省略しました。 すべての表示/非表示関連コードが表示されます。

//the master view controller will be hidden so hook the popover
- (void)splitViewController:(UISplitViewController*)svc willHideViewController:(UIViewController *)aViewController withBarButtonItem:(UIBarButtonItem*)barButtonItem forPopoverController:(UIPopoverController*)pc 
{   
    _popoverShowing = FALSE;
    if(_toolbar == nil) 
    {
        //set title of master button
        barButtonItem.title = @"Title goes here";

        //Impose my selector in between the SVController, and the SVController's default implementation
        _svcTarget = barButtonItem.target;
        _svcAction = barButtonItem.action;
        barButtonItem.target = self;
        barButtonItem.action = @selector(svcToolbarClicked:);

        //create a toolbar
        _toolbar = [[UIToolbar alloc] initWithFrame:CGRectMake(0, 0, 1024, 44)];
        [_toolbar setItems:[NSArray arrayWithObject:barButtonItem] animated:YES];
    }

    //add the toolbar to the details view (the second controller in the splitViewControllers array)
    UIViewController* temp = [_splitViewController.viewControllers objectAtIndex:1];
    [temp.view addSubview:_toolbar];
}

これが私の関数で、ツールバーのクリックに応答します。これは、ユーザーがツールバーボタンをタップして再度タップした場合を処理します。

-(void) svcToolbarClicked: (id)sender
{
    if(_popoverShowing)
    {
        [_popover dismissPopoverAnimated:TRUE];
    }
    else 
    {
        //Perform the default SVController implementation
        [_svcTarget performSelector:_svcAction];
    }
    //Toggle the flag
    _popoverShowing = !_popoverShowing;
}

UISplitViewControllerDelegateの一部の関数

//the master view (non-popover) will be shown again (meaning it is going to landscape orientation)
- (void)splitViewController:(UISplitViewController*)svc willShowViewController:(UIViewController *)aViewController invalidatingBarButtonItem:(UIBarButtonItem *)button 
{
    //remove the toolbar
    [_toolbar removeFromSuperview];
}

// the master view controller will be displayed in a popover (i.e. the button has been pressed, and the popover is about to be displayed.  
//Unfortunately triggers when the popover is ALREADY displayed.
- (void)splitViewController:(UISplitViewController*)svc popoverController:(UIPopoverController*)pc willPresentViewController:(UIViewController *)aViewController 
{   
    _popover = pc; //Grab the popover object  
    _popover.delegate = self;
}

ほとんどの場合、上記のコードで十分です。ただし、ユーザーがポップオーバーを開いてから画面上の他の場所をクリックして閉じると、_popoverShowingブール値に誤った値が含まれるため、ユーザーはツールバーボタンを2回タップしてポップオーバーを再度開く必要があります。これを修正するには、UIPopoverControllerDelegate以下のスニペットのようなメソッドを実装します。

//UIPopoverControllerDelegate method
- (void)popoverControllerDidDismissPopover:(UIPopoverController *)popoverController
{
    _popoverShowing = FALSE;
    _popover = nil;
}

これは、ドキュメントと(私が思うに)StackOverflowに関するUISplitViewControllerの質問のほとんどを掘り下げて理解するのに永遠にかかりました。誰かがそれが役に立つと思うことを願っています。もしそうなら、私は評判ポイントを切望します。;-)

于 2010-04-17T16:13:04.067 に答える
0

たぶん、皆さんはそれを複雑にしすぎているか、皆さんがやりたかったこととはまったく異なる何かを読んだことがあります...しかし、おそらく、これは皆さんがとても難しいことを理解しようとしていたことです:

-(void)togglePopOverController {

if ([popOverController isPopoverVisible]) {

[popOverController dismissPopoverAnimated:YES];

} else {

[popOverController presentPopoverFromBarButtonItem:bbiOpenPopOver permittedArrowDirections:UIPopoverArrowDirectionAny animated:YES];

}

}
于 2010-05-11T18:57:25.000 に答える
-1

エリザベスはこう書いています:

ポップオーバーの外側をタップすると、アイテムを選択せず​​にポップオーバーを非表示にすることができますが、ユーザーがもう一度ボタンをタップすると、ポップオーバーを非表示にしたいと思います。

まず第一に、私がこれから言おうとしていることのどれもが個人的にとられることではないということを言わせてください-それはそのように意味されていません。それはすべて、プログラミングインターフェイスを設計し、Appleヒューマンインターフェイスガイドラインを研究してきたことから来ています(そして、常に正しい方法を教えてくれるグラフィックデザイナーがます)。それは反対の視点として意図されており、暴言としてではありません。

あなたが提案しているのは私にとってUIに関する問題であり、Appleがアプリをレビューするときに問題を引き起こす問題になるでしょう。既知のUIオブジェクトに、通常は実行されない機能を実行させることは想定されていません(たとえば、ボタンが表示されてからビュー/オブジェクト/ウィンドウを解放することありません。これを切り替えます)。

たとえば、ナビゲーションバーの虫眼鏡は検索を意味します(Appleによって定義されています)。彼らは過去に、そして将来も、インターフェースをズームするためにこれを使用するアプリを拒否し続けます。例:AppleはConvertBotまたはThe Odyssey:Trail of Tearsを拒否します(ページで検索してください)。拒否の言語は常に同じです(彼らがあなたの使用法のために引用するものを太字で示しています):

「…標準のiPhone/iPod画面画像を非標準の方法で使用しているため、ユーザーが混乱する可能性があります。標準のiPhoneグラフィック、アクション、および画像の動作を変更したり、それらのグラフィック、アクション、または画像の障害をシミュレートしたりすることは、アプリケーションがヒューマンインターフェイスガイドラインに従うことを要求するiPhone開発者プログラム契約に違反します。」</ p>

また、この機能が本当に必要な場合は、「なぜですか」と自問してください。あなた自身がそれを好きだからなら、私は本当にそれをスキップします。ほとんどのユーザーはこの動作に混乱し、それが使用するオプションであることがわからないため、実際には使用しません。Appleは過去3年間、iPhoneOSユーザーにOSとインターフェイス要素の使用方法をトレーニングするのに費やしました。プログラマーまたはデザイナーとして最後にやりたいことは、アプリの使用方法についてユーザーをトレーニングすることに時間を費やすことです。彼らは通常、あなたのアプリをデバイスから削除し、あなたのやり方を学ぶように強制するのではなく、別の同様のアプリに移動します。

ちょうど私の$.02

于 2010-04-14T21:25:36.643 に答える