AngularJS filters an array of objects using text input depending on the selected choice
I'm having trouble setting up a specific Angularjs filtering setting that includes text input, ng-repeat and select, and love any help can provide.
I have an array of objects like this:
[{ id: '1', firstName: 'Charles', lastName: 'Charlston' }, ...]
I am filtering an array by typing text like this:
<input ng-model="searchText" />
<div ng-repeat="person in people | filter : searchText" ...
Currently this is sorting an array of people objects for the value "any" and it works great.
What I am trying to achieve is to change the property that my <input ng-model="searchText" />
filters the people array based on what is selected <option id="1" label="lastName" selected>Last Name</option>
.
My choice looks like this:
<select class="filterSelect"
ng-model="selectedPropertyOption"
ng-options="prop.name for prop in peopleProperties"></select>
peopleProperties looks like this:
$scope.peopleProperties = [{id: "1", name: "firstName"}, ...];
So instead of typing: "charles" in the input file and getting results that match the property id, fistName or lastName, I need to be able to select an option from select where the option is the property name like "firstName" which I want to filter ... Then whatever is entered as input will only filter objects based on which option was selected.
Hope this makes sense! Any guidance would be much appreciated, thanks in advance!
source to share
This is one of those cases where it is inconvenient and curiously "dirty" (although possible) to specify the filter in the view only.
We need a filter object that can take the following forms:
$scope.filter = { firstName: "foo" };
// or
$scope.filter = { lastName: "foo" };
// or - to reset the "filterBy" property
$scope.filter = { $: "foo" }; // or just "foo"
This is not easy to do in an expression, so it's better to do it in a controller:
$scope.filter = {$: undefined}; // initial non-filtering value
$scope.setFilter = function(){
$scope.filter = {};
$scope.filter[$scope.selectedPropertyOption || '$'] = $scope.searchText;
};
Then call the function setFilter
on every change searchText
to selectedPropertyOption
:
<input ng-model="searchText" ng-change="setFilter()" />
<select ng-model="selectedPropertyOption"
ng-options="prop.name as prop.name for prop in peopleProperties"
ng-change="setFilter()">
<option value="">All Fields</option>
</select>
<div ng-repeat="person in people | filter: filter">
{{person}}
</div>
source to share