0

私は2つの主要なコントローラータイプで構成されるアプリを持っています:

1) UITableViewController - ナビゲーション画面として機能します。2) UINavigationController 内に含まれる UIViewController - メインのアプリ コンテンツを表示します。

TableViewController の内容は次のようになります。

  • ページ1
  • ページ2
  • ページ3 ...など

AppDelegate にプロパティを定義しました - PageViewControllers という配列です。アプリケーションが起動すると、アプリ内の各ページに対して UIViewController の新しいインスタンスが作成されます。

最初のPageのコントローラーは、UINavigationController の rootViewController として設定されます。

ユーザーが UITableView コントローラーで行を選択すると、 UINavigationController はその行に関連するビュー コントローラーにプッシュまたはポップします。(「Page 3」をタップすると、Page 3 のコントローラーにプッシュされます)。

私はこれをうまく機能させています - 唯一の問題は、ナビゲーションスタックをはるかに戻そうとするとアプリが時々クラッシュすることです. たとえば、15ページから2ページへ

私が得ているエラーメッセージは次のとおりです。

*** Terminating app due to uncaught exception 'RuntimeError', reason: 'NSInternalInconsistencyException: Tried to pop to a view controller that doesn't exist.

UINavigationController がいくつかのコントローラーをリリースしている可能性があると思います。UINavigationController の戻るボタンが期待どおりに動作できるように、アプリは以前のコントローラーをすべてメモリに保持すると思いましたか?

これが起こらないようにする方法はありますか、それとも見逃したことがありますか?

アップデート

テーブルの行が選択された後にナビゲーション コントローラーをプッシュ/ポップするコードを次に示します。(ルビモーションです)

def tableView(tableView, didSelectRowAtIndexPath: indexPath)
  # first we need to work out which controller was selected...
  page = Page.current

  currentPageController      = appDelegate.pageControllers[page.absoluteIndex]
  currentPageControllerIndex = appDelegate.pageControllers.index(currentPageController)

  nextPageController      = appDelegate.pageControllers[Page.pageAtIndexPath(indexPath).absoluteIndex]
  nextPageControllerIndex = appDelegate.pageControllers.index(nextPageController)

  case
  # When we're moving forward in the stack... 
  when currentPageControllerIndex < nextPageControllerIndex
    for controller in appDelegate.pageControllers[(currentPageControllerIndex + 1)..nextPageControllerIndex]
      # push the next controller on to the nav stack, only animate if it's the last one
      appDelegate.rootViewControllerNav.pushViewController(controller, animated: controller == nextPageController)        
    end

  # When we're moving backward in the stack...
  when currentPageControllerIndex > nextPageControllerIndex
    appDelegate.rootViewControllerNav.popToViewController(nextPageController, animated: true)

  # When we select the same step again...
  else
    NSLog("Selected the same page")
  end

  # close the side menu afterwards
  appDelegate.rootViewControllerNav.sideMenu.toggleSideMenuPressed(self)
end
4

2 に答える 2

0

「アプリは、UINavigationControllerの戻るボタンが期待どおりに動作できるように、以前のすべてのコントローラーをメモリに保持すると思いましたか?」

前進している限り、これは真実です。新しいView Controllerをプッシュすると、スタック上の前のViewControllerに新しいViewControllerが追加されます。ただし、popViewControllerを実行すると、スタックから削除され、強力な参照がない場合は、割り当てが解除されます。したがって、1-> 2-> 3 ........-> 15に移動してから2にポップすると、機能するはずですが、次のようなことを行うと、次のようになります。

1-> 2-> 3popTo1次にpushto->15、次にpop to 2、2も3ももう存在しません。したがって、テーブル内のセルを選択しているシーケンスに注意を払い、エラーが発生したときに注意する必要があります。この説明に対応しているかどうかを確認してください。

于 2012-11-15T04:13:33.017 に答える
0

ひび割れた!

ここでの問題は、アプリの他の場所にあるロジックにありました。ページがPage.currentPageから設定されていることがわかります。

page = Page.currentPage

Page.currentPageは常に、現在表示されているページに設定する必要があります。

現在のページを設定するコードは、viewDidAppear:animated メソッドではなく、PagesViewController の viewDidLoad メソッドにありました。つまり、ページが表示された場合、Page.currentPage は再度設定されません。

今すぐ修正 - 共有されたアイデアとヒントに感謝します!

于 2012-11-15T10:09:59.860 に答える