1

离子选项卡,选项卡的根 HTML 有“RootTabCtrl”,“Tab1”(带有“Tab1_Ctrl”)有一个表单,其他选项卡被禁用

  1. 用户在 Tab1 上提交表单
  2. Tab1 控制器功能启动。
  3. 控制器函数调用外部函数(不在控制器中)。
  4. 外部函数触发器,它执行一个承诺
  5. 在 promise "results" 中,处理返回的数据
  6. 如果返回数据中的 X 为真,则触发“RootTabCtrl”函数以启用其他禁用的选项卡。
  7. 我可以跟踪触发每一步的控制台消息。

除了以下奇怪的行为外,这一切都有效。在用户再次单击表单提交之前,“RootTabCtrl”不会启用禁用的选项卡......即使我看到控制台消息说它位于 RootTabCtrl 函数的(最后)。我从第一次单击中看到所有相同的控制台消息 - 但第二次是禁用的选项卡再次启用。

如果我在第 4 步中将第 6 步移到承诺之外,并将其放在第 3 步之后(以及在承诺之前),那么所有选项卡都会在第一次单击时启用。但是,这不再考虑 X 的值来确定是否应重新启用其他选项卡。

我可以寻找或不知道会导致这种情况的原因是什么?

应用程序.js:

 .state('tab', {
    url: "/tab",
    abstract: true,
    templateUrl: "templates/tabs.html",
    controller: 'TabsCtrl'
  })

  // Each tab has its own nav history stack:

  .state('tab.tab1', {
    url: '/map',
    views: {
      'tab-1': {
        templateUrl: 'templates/tab-1.html',
        controller: 'tab1Ctrl'
      }
    }
  })

控制器:

.controller('TabsCtrl', function($scope,$rootScope,constants) {
  $scope.constants = constants ;
  $scope.tabControl = { 
    disableRides : true,
    disableBikes : true,
    disableTransit : true
  }

  var refreshFinalizer = $rootScope.$on('updateTabsRefresh', function (event, data) {
    console.log("Refresher 1") ;
     $scope.tabControl.disableTab2 = false;
     $scope.tabControl.disableTab3 = false ;
     console.log("Refresher 2") ;
  });

  $scope.$on('$destroy', function () {
    console.log("Destroy") ;
    refreshFinalizer ();
  });
})

.controller('tab1Ctrl', function($scope,$rootScope) {

  $scope.setInfo= function() {
    getGoogle(document.getElementById('form_data').value,0);
  }
  $scope.enableTabs = function(type) {
    console.log("Here enableTabs1") ;
    $rootScope.$broadcast('updateTabsRefresh');
    console.log("Here enableTabs2") ;    
  }
})

Tab1 有一个表单,点击后执行$scope.setInfo。然后 getGoogle() 在外部 JS 函数中,它调用谷歌地图,如果特定数据 X 为真,则使用 tab1Ctrl $scope.enableTabs() 启用所有其他选项卡:

    function getGoogle(userInfo,clear) {
        console.log("setInfo 1") ;
        geoCoder.geocode({'address': userInfo}, function(results, status) {
          if (status == google.maps.GeocoderStatus.OK) {
            if (results[0]) {
              // extra code removed
              startPointSet = 1;
           // tab1Ctrl html has id of "Tab1" 
angular.element(document.getElementById('Tab1')).scope().enableTabs();
              /* alternative method, worked the same as previous line but with same problem 
              var $sBody = angular.element(document.body) ;
              var $sRootScope = $sBody.injector().get('$rootScope') ;
              $sRootScope.$broadcast('updateTabsRefresh') ;
              */
              console.log("setInfo 2") ;
            }
          } else {
            // extra code removed
            console.log(response) ;
          }
        });
      }
    }

以上所有工作......除了调用 enableTabs (在谷歌响应中)时,即使它正确调用 enableTabs 并且我可以看到从 enableTabs 内触发的 console.log 消息 - 其他选项卡不“启用" 直到第二次单击表单按钮(然后我再次看到所有控制台消息)。我从 getGoogle() 中尝试了 2 种不同的方法,它们的工作方式完全相同 - 第一次单击正确触发了所有功能,但选项卡未启用。第二次单击触发了所有功能,然后启用了选项卡。

4

1 回答 1

1

试试这个先前的答案。你在使用 $http 调用吗?如果是这样,我实际上从来没有这样做过,所以似乎其他原因可能是根本原因。

更新

为这个 GetGoogle 函数调用创建一个Angular 服务怎么样。然后你仍然会在 angular 内部并且可以注入 $rootScope 和你需要的任何其他东西。您需要将此服务注入您的 tab1Ctrl(下面的 myGoggleService)。我也可能只是在 ng-submit 上将表单传回:

html

ng-submit="setInfo(formNameGoesHere)"

控制器

.controller('tab1Ctrl', function($scope, $rootScope, myGoogleService) {
    $scope.setInfo = function(form) {
        myGoogleService.getGoogle(form);
    }
    $scope.enableTabs = function(type) {
        console.log("Here enableTabs1");
        $rootScope.$broadcast('updateTabsRefresh');
        console.log("Here enableTabs2");
    }
});

服务:如果您尚未创建任何内容,则需要像您拥有的任何指令一样在您的 app.js 中注册它,并将它们像常规控制器一样放入您的 index.html 页面中。

.service('myGoggleService', [ '$rootScope', function ($rootScope) {
  this.getGoogle = function(userInfo,clear) {
    console.log("setInfo 1") ;
    geoCoder.geocode({'address': userInfo}, function(results, status) {
        if (status == google.maps.GeocoderStatus.OK) {
            $rootScope.$broadcast("updateTabsRefresh");
        } else {

        }
    });
  }
}}]);

我确实从上面复制了您的代码,然后删除了一些额外的东西只是为了理解这一点。显然无法运行代码,因此可能需要一些错误或细微的更改,但希望这会让你接近。

于 2016-05-31T21:16:04.367 回答