Reputation: 49
Currently I'm working in card filter, but I get jobCards[card].getElementsByClassName is not a function.
const cardHasRequirementFilter = function(card){
for(let requirementInFilter in listForFiltering){
let requirementsByCard = jobCards[card].getElementsByClassName("job-requirements__requirement");
for(let requirementInCard in requirementsByCard){
if(requirementInCard.innerHTML === requirementInFilter.innerHTML ){
return true;
}
}
}
return false;
}
When I call that function i do it this way
jobCards[card].style.display = cardHasRequirementFilter(card)===true?"flex":"none";
I tried with:
jobCards[card].style.display = cardHasRequirementFilter(jobCards[card])===true?"flex":"none";
const cardHasRequirementFilter = function(card){
for(let requirementInFilter in listForFiltering){
let requirementsByCard = card.getElementsByClassName("job-requirements__requirement");
for(let requirementInCard in requirementsByCard){
if(requirementInCard.innerHTML === requirementInFilter.innerHTML ){
return true;
}
}
}
return false;
}
And i get the same error...
I tried on Edge and chrome.
All my code is:
const btnsRequirements = document.getElementsByClassName("job-requirements__requirement");
const jobCards = document.getElementsByClassName("job-list__card-job");
/* All non repetible requirements existent. */
const listRequirements = {};
/* The cards will be filtered by this requirements to be
filtered, if it's empty, then all cards will be shown. */
const listForFiltering = {};
for (let requirement of btnsRequirements) {
let text = requirement.innerHTML;
listRequirements[text] = text;/* Creates a new property with the same value, if already existe, it's overited. */
requirement.addEventListener("click", function () {
let requirementClicked = this.innerHTML;
listForFiltering[requirementClicked] = requirementClicked;
filterCardsByRequirementsChoosed();
}, false);
}
const filterCardsByRequirementsChoosed = function(){
let numEntries = Object.entries(listForFiltering).length;
if ( numEntries === 0){
/* if there's no filter, then show all. */
for(let card of jobCards){
jobCards[card].style.display = "flex";
}
}else{
for(let card in jobCards){
jobCards[card].style.display = cardHasRequirementFilter(card)===true?"flex":"none";
}
}
};
const cardHasRequirementFilter = function(card){
for(let requirementInFilter in listForFiltering){
let requirementsByCard = jobCards[card].getElementsByClassName("job-requirements__requirement");
for(let requirementInCard in requirementsByCard){
if(requirementInCard.innerHTML === requirementInFilter.innerHTML ){
return true;
}
}
}
return false;
}
Upvotes: 2
Views: 417
Reputation: 519
in your loop
for(let card of jobCards)
card is your variable that will represent the elements in jobCards as they are being iterated through. It is not an index.
So you need to do
card.getElementByClassName(...)
card.style.display(...)
EDIT— As per the comment below... you use the for in loop... which iterates over properties of the object. For an array... this will include the indices and other properties such as @length, etc giving you the error.
Upvotes: 1
Reputation:
First look at the filterCardsByRequirementsChoosed
function. You have both for-of
and for-in
loops, but are using them as though they're the same.
The for-of
should be:
for(let card of jobCards){
// jobCards[card].style.display = "flex";
card.style.display = "flex";
}
The for-in
was done correctly, but using for-of
is a little nicer IMO.
So it seemed you were just passing the wrong value to the function in question.
Actually, I do see that you're only calling the problem function in the for-in
loop, and are passing the property name. So you seem to be doing that correctly.
One thing to keep in mind is that your jobCards
is a "live list". So if any of those elements get removed from the DOM, or even if the class you used to fetch them gets removed, those elements will be also removed from the jobCards
list immediately.
Upvotes: 1