0

I have such array of objects:

var cars = [  
   {  
      "carMake":"Audi",
      "models":[  
         "A4",
         "A6",
         "R8"
      ]
   },
   {  
      "carMake":"BMW",
      "models":[  
         "3er",
         "X3",
         "i8",
         "7er"
      ]
   },
   {  
      "carMake":"Toyota",
      "models":[  
         "Corolla",
         "Auris",
         "Yaris",
         "Gt86",
         "Rav4"
      ]
   }
];

And I have tried below AngularJS code for searching:

$scope.searching = '';
$scope.producers = [];
$scope.models = [];

$scope.searchCar = function() {
  $scope.producers = $filter('filter')(cars, function(value) {
    return value.carMake === $scope.searching;
  });
  $scope.models = $filter('filter')(cars, function(value) {
    return angular.forEach(value.models, function(model) {
      return model === $scope.searching;
    });
  });
};

Inside HTML I have:

<label>What do you want to find?
  <input type="text" ng-model="searching" ng-change="searchCar()" placeholder="Search...">
</label>
<ul>
  <li ng-repeat="producer in producers">{{producer}}</li>
</ul>
<ul>
  <li ng-repeat="model in models">{{model}}</li>
</ul>

My code doesn't work as I expected - it only outputs whole cars Array element. For example, when I type "Audi" i got whole "Audi object", although I want separately results for car producers and/or car models that match pattern inside <input>.

I want searching to work like, when I type "Au" then I will see "Audi" in first list and "Auris" in the second. So searching should work as well for cars.carMake as for cars.models[] and present result in both lists (first/left for car producers and second/right for car models).

2
  • have you tried angular inbuilt filter? it's search function for arrays? Commented Aug 6, 2016 at 21:23
  • @JorawarSingh, according to docs.angularjs.org/api/ng/filter/filter I am using JavaScript way. Commented Aug 6, 2016 at 21:24

1 Answer 1

1

I'd suggest you to store the items in separated arrays, then use the filter in view:

(function() {
  angular
    .module("app", [])
    .controller('MainCtrl', MainCtrl);

  MainCtrl.$inject = ['$scope'];

  function MainCtrl($scope) {
    $scope.sensitiveCompare = sensitiveCompare;
    var cars = [  
       {  
          "carMake":"Audi",
          "models":[  
             "A4",
             "A6",
             "R8"
          ]
       },
       {  
          "carMake":"BMW",
          "models":[  
             "3er",
             "X3",
             "i8",
             "7er"
          ]
       },
       {  
          "carMake":"Toyota",
          "models":[  
             "Corolla",
             "Auris",
             "Yaris",
             "Gt86",
             "Rav4"
          ]
       }
    ];

    $scope.producers = cars.map(function(car) {
      return car.carMake;
    });

    $scope.models = [];
    
    cars.forEach(function(car) {
      $scope.models = $scope.models.concat(car.models);
    });


    function sensitiveCompare(input, search) {
      return ('' + input).indexOf('' + search) > -1;
    }
  }
})();
<!DOCTYPE html>
<html ng-app="app">

<head>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.8/angular.min.js"></script>
</head>

<body ng-controller="MainCtrl">
  <label>What do you want to find?
    <input type="text" ng-model="searching" ng-change="searchCar()" placeholder="Search...">
  </label>
  <ul>
    <li ng-repeat="producer in producers | filter: searching: sensitiveCompare" ng-bind="producer"></li>
  </ul>
  <ul>
    <li ng-repeat="model in models | filter: searching: sensitiveCompare" ng-bind="model"></li>
  </ul>
</body>

</html>

EDIT:

If you really want to create your custom function for this, check this:

(function() {
  angular
    .module("app", [])
    .controller('MainCtrl', MainCtrl);

  MainCtrl.$inject = ['$scope', '$filter'];

  function MainCtrl($scope, $filter) {
    $scope.searchCar = searchCar;
    var cars = [  
       {  
          "carMake":"Audi",
          "models":[  
             "A4",
             "A6",
             "R8"
          ]
       },
       {  
          "carMake":"BMW",
          "models":[  
             "3er",
             "X3",
             "i8",
             "7er"
          ]
       },
       {  
          "carMake":"Toyota",
          "models":[  
             "Corolla",
             "Auris",
             "Yaris",
             "Gt86",
             "Rav4"
          ]
       }
    ];
    
    $scope.producers = [];
    $scope.models = [];
    
    function searchCar() {
      $scope.producers = $filter('filter')(cars, function(car) {
        return car.carMake.indexOf($scope.searching) !== -1;
      });
      
      $filter('filter')(cars, function(car) {
        $scope.models = car.models.filter(function(model) {
          return model.indexOf($scope.searching) !== -1;
        })
      });
    }
  }
})();
<!DOCTYPE html>
<html ng-app="app">

<head>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.8/angular.min.js"></script>
  <link rel="stylesheet" href="style.css">
  <script src="script.js"></script>
</head>

<body ng-controller="MainCtrl">
  <label>What do you want to find?
    <input type="text" ng-model="searching" ng-change="searchCar()" placeholder="Search...">
  </label>
  <ul>
    <li ng-repeat="producer in producers" ng-bind="producer.carMake"></li>
  </ul>
  <ul>
    <li ng-repeat="model in models" ng-bind="model"></li>
  </ul>
</body>

</html>

Sign up to request clarification or add additional context in comments.

3 Comments

Ok, but why You propose using filter in HTML instead of using $filter in JavaScript? Additional question - how to filter including case sensitiveness?
Well, I'd prefer since Angular already can do it for me, for what should I write my own method? To include case sensitive compare you should add a little method as I added above. Check it please.
Thank You. Could You also show "alternative" way with using $filter('filter')(array, expression, comparator, anyPropertyKey) presented at docs.angularjs.org/api/ng/filter/filter as I was trying to filter it using $filter?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.