首页 文章

如何在页面加载时执行AngularJS控制器功能?

提问于
浏览
341

目前我有一个Angular.js页面,允许搜索和显示结果 . 用户单击搜索结果,然后单击后退按钮 . 我希望再次显示搜索结果,但我无法确定如何触发搜索执行 . 这是详细信息:

  • 我的Angular.js页面是一个搜索页面,带有搜索字段和搜索按钮 . 用户可以手动键入查询并按下按钮,并触发ajax查询并显示结果 . 我用搜索词更新了URL . 一切正常 .

  • 用户点击搜索结果并转到其他页面 - 这也可以正常工作 .

  • 用户单击后退按钮,然后返回到我的角度搜索页面,并显示正确的URL,包括搜索词 . 一切正常 .

  • 我已将搜索字段值绑定到URL中的搜索词,因此它包含预期的搜索词 . 一切正常 .

如何在没有用户按“搜索按钮”的情况下再次执行搜索功能?如果是jquery那么我会在documentready函数中执行一个函数 . 我看不到Angular.js的等价物 .

13 回答

  • 18

    你可以使用angular的$ window对象:

    $window.onload = function(e) {
      //your magic here
    }
    
  • 132

    另一种选择:

    var myInit = function () {
        //...
    };
    angular.element(document).ready(myInit);
    

    (通过https://stackoverflow.com/a/30258904/148412

  • 4

    一方面,@ Mark-Rajcok说你可以逃脱私人内在功能:

    // at the bottom of your controller
    var init = function () {
       // check if there is query in url
       // and fire search in case its value is not empty
    };
    // and fire it after definition
    init();
    

    你也可以看一下ng-init指令 . 实施将很像:

    // register controller in html
    <div data-ng-controller="myCtrl" data-ng-init="init()"></div>
    
    // in controller
    $scope.init = function () {
        // check if there is query in url
        // and fire search in case its value is not empty
    };
    

    但要注意它,因为angular documentation implies (since v1.2)不要使用 ng-init . 但是,这取决于您的应用程序的架构 .

    当我想将一个值从后端传递到angular app时,我使用 ng-init

    <div data-ng-controller="myCtrl" data-ng-init="init('%some_backend_value%')"></div>
    
  • 2

    您可以将搜索结果保存在一个可以在任何地方使用但在导航到另一个页面时无法清除的公共服务中,然后您可以使用保存的数据设置搜索结果以单击后退按钮

    function search(searchTerm) {
        // retrieve the data here;
        RetrievedData = CallService();
        CommonFunctionalityService.saveSerachResults(RetrievedData);
    }
    

    对于你的后门按钮

    function Backbutton() {
        RetrievedData = CommonFunctionalityService.retrieveResults();
    }
    
  • 26
    angular.element(document).ready(function () {
    
        // your code here
    
    });
    
  • 3

    我永远无法让 $viewContentLoaded 为我工作, ng-init 应该只用在 ng-repeat (根据文档),并且如果代码依赖于一个没有的元素,也直接在控制器中调用函数会导致错误已定义 .

    这就是我的工作,它对我有用:

    $scope.$on('$routeChangeSuccess', function () {
      // do something
    });
    

    除非你使用 ui-router . 那就是:

    $scope.$on('$stateChangeSuccess', function () {
      // do something
    });
    
  • 59

    如果要观察要更改的viewContentLoaded DOM对象然后执行某些操作,则可以执行此操作 . 使用$ scope . $ on也可以,但不同,特别是当你的路由有一个页面模式时 .

    $scope.$watch('$viewContentLoaded', function(){
        // do something
     });
    
  • 29

    如果你有一个特定于该页面的控制器,还有另一种选择:

    (function(){
        //code to run
    }());
    
  • 3

    使用$ routeProvider时,您可以解析.state并引导您的服务 . 这就是说,只有在解决了您的服务之后,您才会加载Controller和View:

    UI的路线

    .state('nn', {
            url: "/nn",
            templateUrl: "views/home/n.html",
            controller: 'nnCtrl',
            resolve: {
              initialised: function (ourBootstrapService, $q) {
    
                var deferred = $q.defer();
    
                ourBootstrapService.init().then(function(initialised) {
                  deferred.resolve(initialised);
                });
                return deferred.promise;
              }
            }
          })
    

    服务

    function ourBootstrapService() {
    
     function init(){ 
        // this is what we need
     }
    }
    
  • 3

    发现Dmitry Evseev的回答非常有用 .

    Case 1 : Using angularJs alone:
    要在页面加载时执行方法,可以在视图中使用 ng-init 并在控制器中声明init方法,并且根据angular Docs on ng-init,不建议使用较重的函数:

    可以滥用此指令将不必要的逻辑量添加到模板中 . ngInit只有少数适当的用途,例如用于别名ngRepeat的特殊属性,如下面的演示所示;并通过服务器端脚本注入数据 . 除了这几种情况,您应该使用控制器而不是ngInit来初始化作用域上的值 .

    HTML:

    <div ng-controller="searchController()">
        <!-- renaming view code here, including the search box and the buttons -->
    </div>
    

    Controller:

    app.controller('SearchCtrl', function(){
    
        var doSearch = function(keyword){
            //Search code here
        }
    
        doSearch($routeParams.searchKeyword);
    })
    

    Warning : 不要将此控制器用于另一个意图用于不同意图的视图,因为它会导致搜索方法也在那里执行 .

    Case 2 : Using Ionic:
    上面的代码将起作用,只需确保在 route.js 中禁用视图缓存:

    route.js

    .state('app', {
        url           : '/search',
        cache         : false, //disable caching of the view here
        templateUrl   : 'templates/search.html'   ,
        controller    : 'SearchCtrl'
      })
    

    希望这可以帮助

  • 3

    Dimitri 's/Mark'的解决方案对我不起作用,但使用$timeout函数似乎可以很好地确保您的代码仅在呈现标记后运行 .

    # Your controller, including $timeout
    
    var $scope.init = function(){
     //your code
    }
    
    $timeout($scope.init)
    

    希望能帮助到你 .

  • 42

    试试这个?

    $scope.$on('$viewContentLoaded', function() {
        //call it here
    });
    
  • 409

    我有同样的问题,只有这个解决方案适合我(它在一个完整的DOM加载后运行一个函数) . 我在加载页面后使用它来滚动到锚点:

    angular.element(window.document.body).ready(function () {
    
                            // Your function that runs after all DOM is loaded
    
                        });
    

相关问题