web-dev-qa-db-ja.com

ビューが開かれる/表示されるたびにコントローラー関数を実行する

下部に3つのイオンタブがある古典的な3ボタンメニューを使用する、angular + ionicのアプリを作成しています。ユーザーがタブをクリックすると、ui-routerを介してそのテンプレートが開きます。

このような状態があります:

$stateProvider
  .state('other', {
    url: "/other",
    abstract: true,
    templateUrl: "templates/other/other.html"
})

テンプレートでは、次のようなことを行います。

<ion-nav-view name="other" ng-init="doSomething()"></ion-nav-view>

コントローラーでdoSomething()関数を記述し、そこで手動で呼び出すことができることを認識しています。それは私にも同じ問題を与えます。誰かがそのビューを開くたびに、doSomething()関数を複数回呼び出す方法がわからないようです。

現在、doSomething()関数は問題なく呼び出されますが、ビュー/タブがユーザーによって初めて開かれたときのみです。ユーザーがそのビューまたはタブを開くたびに(位置情報を更新するために)関数を呼び出したいです。

それを実装する正しい方法は何ですか?

手伝ってくれてありがとう!

79
Jorre

特定のコントローラーをビューに割り当てた場合、ビューが読み込まれるたびにコントローラーが呼び出されます。その場合、コントローラーが呼び出されるとすぐにコントローラーでいくつかのコードを実行できます。たとえば、次のようになります。

<ion-nav-view ng-controller="indexController" name="other" ng-init="doSomething()"></ion-nav-view>

そしてコントローラーで:

app.controller('indexController', function($scope) {
    /*
        Write some code directly over here without any function,
        and it will be executed every time your view loads.
        Something like this:
    */
    $scope.xyz = 1;
});

Edit:状態の変化を追跡し、ルートが変更されて特定のルートが訪問されたときにコードを実行しようとする場合があります。次に例を示します。

$rootScope.$on('$stateChangeSuccess', 
function(event, toState, toParams, fromState, fromParams){ ... })

詳細については、 状態変更イベント を参照してください。

45

デフォルトでは、コントローラーはキャッシュであったため、コントローラーは1回しか起動しませんでした。特定のコントローラーのキャッシュをオフにするには、.config(..).stateを変更し、cacheオプションをfalseに設定する必要があります。例:

  .state('myApp', {
    cache: false,
    url: "/form",
    views: {
      'menuContent': {
        templateUrl: "templates/form.html",
        controller: 'formCtrl'
      }
    }
  })

詳細については、 http://ionicframework.com/docs/api/directive/ionNavView/ をご覧ください。

86
Yakob Ubaidi

AlexMart からの回答とリンクをフォローアップすると、次のように機能します。

.controller('MyCtrl', function($scope) {
  $scope.$on('$ionicView.enter', function() {
     // Code you want executed every time view is opened
     console.log('Opened!')
  })
})
49
jczaplew

私は同じ問題に直面しました、そして、ここで私は同じ振る舞いの他の皆にこの振る舞いの理由を残します。

ライフサイクルを見る

パフォーマンスを改善するために、ビュー要素とスコープデータをキャッシュするIonicの機能を改善しました。コントローラーが初期化されると、アプリの存続期間中維持されます。単に非表示になり、時計サイクルから削除されます。スコープを再構築するわけではないため、監視サイクルに再び入るときにリッスンする必要があるイベントを追加しました。

詳細な説明と$ ionicViewイベントを確認するには、次のURLにアクセスしてください。 http://ionicframework.com/blog/navigating-the-changes/

12
AlexMart

cache-view = "false"でビューキャッシュを無効にしないのはなぜですか?

ビューで、これを次のようなion-nav-viewに追加します。

<ion-nav-view name="other" cache-view="false"></ion-nav-view>

または、stateProviderで:

$stateProvider.state('other', {
   cache: false,
   url : '/other',
   templateUrl : 'templates/other/other.html'
})

どちらでも、コントローラーが常に呼び出されます。

8
Diogo Medeiros

たとえば、@ Michael Trouwには、

コントローラ内にこのコードを配置します。これは、この状態に入るかアクティブになるたびに実行されます。キャッシュを無効にすることを心配する必要はなく、より良いアプローチです。

.controller('exampleCtrl',function($scope){
$scope.$on('$ionicView.enter', function(){
        // Any thing you can think of
        alert("This function just ran away");   
    });
})

ビューが表示される前に実行される$ ionicView.beforeEnter->のような柔軟性の例がさらにあります。そして、さらにいくつかあります。

5
Wang'l Pakhrin

上記のビュー要素とスコープデータをキャッシュするIonicの機能を考慮すると、ビューが読み込まれるたびにコントローラーを実行する場合、これは別の方法かもしれません。以下を実行することにより、ionicによって使用されるキャッシュメカニズムをグローバルに無効にできます。

$ionicConfigProvider.views.maxCache(0);

それ以外の場合、私がそれを機能させた方法は

$scope.$on("$ionicView.afterLeave", function () {
     $ionicHistory.clearCache();
}); 

これは、再度入力するたびにビューを離れてコントローラーを再実行する前にキャッシュをクリアすることです。

2
Rajush

これはおそらくあなたが探していたものです:

Ionicはデフォルトでビューをキャッシュし、したがってコントローラーをキャッシュします(最大10) http://ionicframework.com/docs/api/directive/ionView/

ionicイベントに基づいてコントローラーに特定の処理を実行させるためにフックできるイベントがあります。例についてはこちらをご覧ください: http://ionicframework.com/blog/navigating-the-changes/

1
Michael Trouw

カメラタブを選択するとすぐにネイティブカメラをロードしようとしていたionicで同様の問題が発生しました。コントローラを(tabs.htmlの)カメラタブのイオンビューコンポーネントに設定し、カメラをロードする$ scopeメソッド(addImage)を呼び出すことで問題を解決しました。

Www/templates/tabs.html

  <ion-tab title="Camera" icon-off="ion-camera" icon-on="ion-camera" href="#/tab/chats" ng-controller="AddMediaCtrl" ng-click="addImage()">
    <ion-nav-view  name="tab-chats"></ion-nav-view>
  </ion-tab>

AddMediaCtrlで定義されているaddImageメソッドは、ユーザーが[カメラ]タブをクリックするたびにネイティブカメラをロードします。 notこれを機能させるためにangularキャッシュ内の何かを変更する必要がありました。これがお役に立てば幸いです。

0
chukkwagon