Reputation: 797
I'm using the following filter to remove accents from the word inputed by the user on an input field, and then use the resulting string on the filter.
.filter('removeAcentos', function(){
return function (source) {
var accent = [
/[\300-\306]/g, /[\340-\346]/g, // A, a
/[\310-\313]/g, /[\350-\353]/g, // E, e
/[\314-\317]/g, /[\354-\357]/g, // I, i
/[\322-\330]/g, /[\362-\370]/g, // O, o
/[\331-\334]/g, /[\371-\374]/g, // U, u
/[\321]/g, /[\361]/g, // N, n
/[\307]/g, /[\347]/g, // C, c
],
noaccent = ['A','a','E','e','I','i','O','o','U','u','N','n','C','c'];
for (var i = 0; i < accent.length; i++){
source = source.replace(accent[i], noaccent[i]);
}
return source;
};
})
And the code in the view is:
<input type="text" id="curso" name="curso" ng-model="ctrl.curso" validate>
<ul>
<li ng-repeat="curso in ctrl.arrayCursos | removeAcentos: ctrl.curso">
...
</li>
</ul>
However, I get the error "source is undefined" and I don't understand why. I also can't use a function inside my controller to be the filter since I'm going to use it in more controllers. I'd like to find where's the error on my code.
ctrl.curso
is predefined when the user enters the page, so I don't understand the 'source is undefined' error, since ctrl.curso
is always defined.
ctrl.curso
is get via $http request, in case it's relevant.
I was using |filter: ctrl.curso
before, however know I need to convert ctrl.curso to a string without accents and filtering the list based on this string.
Just to clarify, I'm looking for to filter the array based on the word inputed by the user. However, first I want to convert this word to a string without accents and then apply the filter itself. For example, If the user types the word 'espécie', I want to filter based on the string 'especie'.
Upvotes: 2
Views: 8076
Reputation: 1289
You need to chain filters. First, you need to remove the accent on the user input:
search | removeAcentos
Then you want to filter your array based on this new value:
filter: (search | removeAcentos)
Note the parenthesis to ensure filters are applied in the correct order.
Result of the updated ng-repeat:
<li ng-repeat="curso in ctrl.arrayCursos | filter: (search | removeAcentos)" />
{{ curso }}
</li>
Link to Working JSFiddle
Upvotes: 5
Reputation: 17579
You are not using your filter right.
If you are going to filter collection - use filter for collection and return new collection where property will be filtered off of accents
If you want to use filter for display - don't apply filter to ng-repeat , apply it to your other binding, ie that is your new html:
<li ng-repeat="curso in ctrl.arrayCursos ">
{{ ctrl.curso | removeAcentos }}
</li>
Upvotes: 0
Reputation: 28750
Just add in the check:
.filter('removeAcentos', function(){
return function (source) {
if(!angular.isDefined(source)){ return; }
var accent = [
/[\300-\306]/g, /[\340-\346]/g, // A, a
/[\310-\313]/g, /[\350-\353]/g, // E, e
/[\314-\317]/g, /[\354-\357]/g, // I, i
/[\322-\330]/g, /[\362-\370]/g, // O, o
/[\331-\334]/g, /[\371-\374]/g, // U, u
/[\321]/g, /[\361]/g, // N, n
/[\307]/g, /[\347]/g, // C, c
],
noaccent = ['A','a','E','e','I','i','O','o','U','u','N','n','C','c'];
for (var i = 0; i < accent.length; i++){
source = source.replace(accent[i], noaccent[i]);
}
return source;
};
})
Upvotes: 0