2016-07-27 7 views
11

私はUISearchControllerを持つテーブルビューコントローラを持っていて、をtableView.tableHeaderViewと設定しています。検索結果を更新するときには、beginUpdatesおよびendUpdatesと関連する方法を使用して、テーブルビューのデータを更新します。beginUpdates/endUpdatesを使用すると、tableHeaderViewからUISearchBarが消える

これにより、検索バーが表示されなくなります。 tableHeaderViewは検索バーと同じサイズの空白の汎用UIViewに設定されています。 beginUpdates/endUpdatesの手順の代わりにreloadDataを使用するだけであれば、すべて問題ありません。

テーブルビューコントローラは、通常のビューコントローラに組み込まれています。ナビゲーションコントローラは含まれていません。これは、問題を再現するために必要なテーブルビューコントローラの全体の実装です:

- (void)viewDidLoad 
{ 
    [super viewDidLoad]; 

    self.searchController = [[UISearchController alloc] initWithSearchResultsController:nil]; 
    self.searchController.searchResultsUpdater = self; 
    self.searchController.dimsBackgroundDuringPresentation = NO; 

    self.tableView.tableHeaderView = self.searchController.searchBar; 
} 

- (void)updateSearchResultsForSearchController:(UISearchController *)searchController 
{ 
    [self.tableView beginUpdates]; 
    [self.tableView endUpdates]; 
} 

は、なぜこれが検索バーが空白のビューに置き換えられる原因んし、どのようにそれを回避することができますか?

+0

あなたのviewController /ナビゲーションコントローラの "半透明"プロパティを変更しようとしましたか?私はこの問題を一度覚えていたことを覚えています。そして、私が正しく「半透明」を思い出すと、それはそれと関係がありました。 – MCMatan

答えて

0

最初にUISearchController's searchBarをクリックすると、searchBarのアニメーション化に約0.5秒かかります。しかし、self.tableView.endUpdates()はすぐにデリゲートメソッドによって呼び出され、アニメーションは中断されました。
検索バーは、アニメーションの真ん中で立ち往生し、あなたはそれがUIだ見ることができない。
enter image description here

この問題を回避するには、検索バーがアニメーションであるかどうかを確認し、それが中だときself.tableView.endUpdates()を遅らせることです。

func updateSearchResultsForSearchController(searchController: UISearchController){ 
    self.tableView.beginUpdates() 
    //Do some updates 

    if !searchController.searchBar.showsCancelButton{ 
     self.tableView.performSelector(#selector(UITableView.endUpdates), withObject: nil, afterDelay: 1) 

    }else{ 
     self.tableView.endUpdates() 
    } 
} 
+0

あなたの答えをありがとう。私はあなたがアニメーションについて何かをしていると思う。私は '[CATransaction setCompletionBlock:]'のようなトリックを試しましたが、役に立たない。あなたの回避策は特にハッキーなようで、元の問題ではうまくいきません。おそらく、私が提供した再現可能な例と同じように考案されたものではなく、 'beginUpdates'と' endUpdates'の間にもっと多くのことがあるからでしょう。 –

+0

その場合は、別のtableViewControllerで 'UISearchController'を初期化し、この2番目のtableViewControllerですべての更新を行うようにしてください。 – wj2061

+0

'[[UISearchController alloc] initWithSearchResultsController:...]'のように?私はそれが解決策だと思いますが、ジェスチャーなどの元のテーブルビューにすべての機能を関連付けたいと思います。他の方法がない場合、リファクタリングで解決できないものは何もありません。 –

0

beginUpdates, endUpdates and reloadData

beginUpdatesについて少しリビジョン:を:一連の方法は、挿入、削除することを呼び出し、またはテーブルビューの行やセクションを選択し開始します。 後続の挿入、削除、および選択操作(cellForRowAtIndexPath:やindexPathsForVisibleRowsなど)を同時にアニメーション化する場合は、このメソッドを呼び出します。また、このメソッドの後にendUpdatesメソッドを使用して、セルをリロードすることなく行の高さの変化をアニメートすることもできます。このグループのメソッドは、endUpdatesの呼び出しで終了する必要があります。これらのメソッドのペアはネストすることができます。このブロック内で挿入、削除、および選択呼び出しを行わないと、行数などの表属性が無効になることがあります。グループ内ではreloadDataを呼び出さないでください。このメソッドをグループ内で呼び出す場合は、自分でアニメーションを実行する必要があります。

endUpdates:テーブルビューの行とセクションを挿入、削除、選択、または再ロードする一連のメソッド呼び出しを終了します。 このメソッドを呼び出すと、beginUpdatesで始まり、テーブルビューの行とセクションを挿入、削除、選択、および再ロードする操作からなる一連のメソッド呼び出しを囲むことができます。 endUpdatesを呼び出すと、UITableViewは操作を同時にアニメーション化します。 beginUpdatesとendUpdatesの呼び出しはネストできます。このブロック内で挿入、削除、および選択呼び出しを行わないと、行数などの表属性が無効になる可能性があります。

reloadData:テーブルビューの行とセクションをリロードします。 このメソッドを呼び出して、セル、セクションのヘッダーとフッター、インデックス配列など、テーブルを構成するために使用されるすべてのデータを再読み込みします。効率を上げるために、テーブルビューは表示されている行のみを再表示します。リロードの結果としてテーブルが縮小する場合、オフセットを調整します。テーブルビューのデリゲートまたはデータソースは、テーブルビューにデータを完全に再ロードさせたい場合にこのメソッドを呼び出します。特にbeginUpdatesとendUpdatesの呼び出しで実装されたアニメーションブロック内で行を挿入または削除するメソッドでは呼び出さないでください。

今すぐ検索の場合には、我々は行は毎回検索結果データが異なるだろうにも影響を与えるために起こっているかわからない、私は1つがその使用など

[self.tableView beginUpdates]; 
[self.tableView endUpdates]; 

を使用してはならないと考えていたときテーブルビューでinsert, update or delete操作を実行していて、そのindexPathを知っています。

[self.tableView reloadData];を使用すると、tableviewの表示行またはセクションのみが更新されるため、改善されます。 AppleのサンプルコードTable Search with UISearchControllerも参照してください。reloadDataもお勧めします。

それぞれ変更してください。あなたは良いです。

ハッピーコーディング:)

+0

'reloadData'を使用すると、問題が解消されることがわかりましたが、なぜそれが' beginUpdates'と 'endUpdates'を使用できないのか説明していません。 –

+0

@Håvardthats私が説明したこと、 'beginUpdatesとendUpdates'と' reloadData'をいつ使うのか。 –

関連する問題