AngularJS在View Reload上丢失了选定的项目(参数丢失的数据类型)

时间:2015-01-27 22:39:06

标签: angularjs select angular-ui-router single-page-application selecteditem

我在Angular SPA中遇到问题,当重新加载视图时,select正在丢失所选项目。所选项目值是正确的。这是一个典型的搜索/结果场景,所以我必须遗漏一些基本的东西。

角度模块(这里很简洁)设置了ui路由和状态,用于确定要加载的视图和控制器等:

var DomainApp = angular.module('DomainApp', ['ui.router', 'ui.bootstrap', 'angularValidator']);

// add controllers, services, and factories
DomainApp.controller('ProductsController', ProductsController);
DomainApp.service('ProductsService', ProductsService);

var configFunction = function ($stateProvider, $httpProvider, $locationProvider) {

    $stateProvider
        .state('productSearch', {
            url: '/products',
            views: {
                "searchView": {
                    templateUrl: '/Templates/products/Search.html',
                    controller: ProductsController
                }
            }
        })
        .state('productResults', {
            url: '/products/Results?categoryID',
            views: {
                "searchView": {
                    templateUrl: '/Templates/products/Search.html',
                    controller: ProductsController
                }
            }
        })
    }
    configFunction.$inject = ['$stateProvider', '$httpProvider', '$locationProvider'];

    DomainApp.config(configFunction);

产品控制器:

var ProductsController = function($scope, $stateParams, $state, $location, ProductsService) {
    // data for search operations
    $scope.searchQuery = {
        categoryID: $stateParams.categoryID || 0,
        categories: null
    };

    // init api
    $scope.init = function () {
        var categoryResult = ProductsService.getCategories(0);
        categoryResult.then(function(result) {
            if (result.isSuccess) {
                $scope.searchQuery.categories = result.data.Items;
            } else {
                $scope.status.isError = true;
                $scope.status.errorMessage = result.message;
            }
        });
    }
}

ProductsController.$inject = ['$scope', '$stateParams', '$state', '$location', 'ProductsService'];

产品服务:

var ProductsService = function ($http, $q) {
    this.getCategories = function (categoryID) {
        var deferredObject = $q.defer();
        var results = {
            isSuccess: true,
            message: '',
            data: null
        }

        $http.get('/api/categories/list/100' + ',' + categoryID).
            success(function (data) {
                results.data = data;
                deferredObject.resolve(results);
            }).
            error(function (data, status, headers, config) {
                results.isSuccess = false;
                results.message = 'Could not get Category list:';
                for (var i = 0; i < data.length; i++) {
                    results.message = results.message + ' ' + data[i].Message;
                }
                deferredObject.resolve(results);
            });

        return deferredObject.promise;
    };
}

ProductsService.$inject = ['$http', '$q'];

产品搜索模板(查看):

<div class="container-fluid searchbar" data-ng-init="init()">
    <h2>Product Search</h2>
    <div class="row top5">
        <div class="col-md-5">
            <label for="category">Category:</label><input type="text" class="form-control" maxlength="40" id="categoryID" ng-model="searchQuery.categoryID" />
            <select class="form-control" name="category" ng-model="searchQuery.categoryID">
                <option value="0">Any</option>
                <option ng-repeat="item in searchQuery.categories" value="{{item.CategoryID}}">{{item.CategoryName}}</option>
            </select>
        </div>
    </div>
    <div class="row top15">
        <div class="col-md-12">
            <a class="btn btn-default" ui-sref="productResults({categoryID: searchQuery.categoryID})">Search</a>
        </div>
    </div>
</div>

在视图中,选择值由data-ng-init="init()"填充,input框和select下拉列表绑定到同一模型项ng-model="searchQuery.categoryID"

在选择类别后加载视图时会发生什么,该值是丢失的,并且选择将恢复为“任何”。文本框具有正确的选定值。我确认select已绑定到模型元素,因为更改input中的值会更改select中的所选项目。在重新加载时,我可以看到select闪烁,看起来它有一段时间的选定值然后丢失它。

修改:总之,所选类别仅作为select中的所选项目“丢失”。所选类别值在网址和input文本框中正确显示。这不是参考比较问题,因为选择选项值为item.CategoryID而不是item类别对象。

我在这里做错了什么?如何将select与绑定值分离和/或我设置绑定错误?

顺便说一句,我还尝试ng-options代替ng-repeat来设置select,但在这种情况下,更改input中的值没有任何影响。

1 个答案:

答案 0 :(得分:1)

此问题实际上是$stateParams中的bug,其中整数的数据类型丢失,并成为字符串。这个问题应该在Angular UI路由器的0.2.12版本中得到修复,但是我仍然在0.2.13中看到了这个问题,并且必须通过将参数值转换回数字来解决这个问题。

具有Number功能的更新产品控制器:

var ProductsController = function($scope, $stateParams, $state, $location, ProductsService) {
    // data for search operations
    $scope.searchQuery = {
        categoryID: Number($stateParams.categoryID) || 0,
        categories: null
    };

    // init api
    $scope.init = function () {
        var categoryResult = ProductsService.getCategories(0);
        categoryResult.then(function(result) {
            if (result.isSuccess) {
                $scope.searchQuery.categories = result.data.Items;
            } else {
                $scope.status.isError = true;
                $scope.status.errorMessage = result.message;
            }
        });
    }
}

ProductsController.$inject = ['$scope', '$stateParams', '$state', '$location', 'ProductsService'];