JS Dynamic array di filtri e concatenamenti di oggetti [duplicato]
Ho questa serie di oggetti
const bnb = [
{
"id": "id1",
"img": ["tres", "dos", "uno"],
"title": "one",
"city": "texas",
"saved": false,
"tags": ["bath"]
},
{
"id": "id2",
"img": ["quatro", "uno", "tres"],
"title": "two",
"city": "denver",
"saved": false,
"tags": ["wc"]
},
{
"id": "id3",
"img": ["uno", "dos", "tres"],
"title": "three",
"city": "vancouver",
"saved": false,
"tags": ["wc", "bath"]
},
{
"id": "id4",
"img": ["dos", "uno", "tres"],
"title": "four",
"city": "berlin",
"saved": false,
"tags": ["bath", "parking"]
},
{
"id": "id5",
"img": ["tres", "uno", "quatro"],
"title": "five",
"city": "paris",
"saved": false,
"tags": ["loft", "parking", "kitchen"]
},
{
"id": "id6",
"img": ["quatro", "uno", "tres"],
"title": "six",
"city": "barcelona",
"saved": false,
"tags": ["bath", "wc"]
},
{
"id": "id7",
"img": ["uno", "tres", "quatro"],
"title": "seven",
"city": "seul",
"saved": false,
"tags": ["parking", "wc", "kitchen"]
}
]
E vorrei filtrare l'elenco per tag. ad esempio, quando clicco sulla casella di controllo, l'elenco dovrebbe fornire un array filtrato in base al valore selezionato. Quando clicco sulla casella di controllo, crea un nuovo array con il valore cliccato, ad esempio let checked = ["parking", "kitchen"]per abbinare i tag oggetto in bnb
<input type="checkbox" value="parking">Parking<br>
<input type="checkbox" value="kitchen">Kitchen<br>
...
So che potrei usare la funzione di filtro come questa, ma non filtra l'array.
let bnblist = bnb.filter(o => o.tags.includes(checked);
Un'altra cosa è che il filtraggio dovrebbe sottrarre array, ad esempio se ho selezionato ["parking", "kitchen"]dovrebbe restituire id5 e id7. Fondamentalmente è simile all'operatore &&, ma ha bisogno di due valori per essere selezionati e ci sono più caselle di controllo e non so quanti utenti vogliono selezionare.
let bnblist = bnb.filter(o => o.tags === "parking" && "kitchen");
Risposte
Puoi usare questo codice.
let bnb = [{"id":"id1","img":["tres","dos","uno"],"title":"one","city":"texas","saved":false,"tags":["bath"]},{"id":"id2","img":["quatro","uno","tres"],"title":"two","city":"denver","saved":false,"tags":["wc"]},{"id":"id3","img":["uno","dos","tres"],"title":"three","city":"vancouver","saved":false,"tags":["wc","bath"]},{"id":"id4","img":["dos","uno","tres"],"title":"four","city":"berlin","saved":false,"tags":["bath","parking"]},{"id":"id5","img":["tres","uno","quatro"],"title":"five","city":"paris","saved":false,"tags":["loft","parking","kitchen"]},{"id":"id6","img":["quatro","uno","tres"],"title":"six","city":"barcelona","saved":false,"tags":["bath","wc"]},{"id":"id7","img":["uno","tres","quatro"],"title":"seven","city":"seul","saved":false,"tags":["parking","wc","kitchen"]}]
let checked = ["parking", "kitchen"]
let bnblist = bnb.filter(o => {
let res = 0;
o.tags.forEach(tag => res += checked.includes(tag));
return res == checked.length && o;
})
console.log(bnblist)
Devi solo aggiungere un everymetodo che itererà sui tag selezionati e verificherà se questi sono inclusi nei tag dell'elemento corrente del filtro.
const bnb = [{"id":"id1","img":["tres","dos","uno"],"title":"one","city":"texas","saved":false,"tags":["bath"]},{"id":"id2","img":["quatro","uno","tres"],"title":"two","city":"denver","saved":false,"tags":["wc"]},{"id":"id3","img":["uno","dos","tres"],"title":"three","city":"vancouver","saved":false,"tags":["wc","bath"]},{"id":"id4","img":["dos","uno","tres"],"title":"four","city":"berlin","saved":false,"tags":["bath","parking"]},{"id":"id5","img":["tres","uno","quatro"],"title":"five","city":"paris","saved":false,"tags":["loft","parking","kitchen"]},{"id":"id6","img":["quatro","uno","tres"],"title":"six","city":"barcelona","saved":false,"tags":["bath","wc"]},{"id":"id7","img":["uno","tres","quatro"],"title":"seven","city":"seul","saved":false,"tags":["parking","wc","kitchen"]}]
let checked = ["parking", "kitchen"]
const result = bnb.filter(({ tags }) => checked.every(tag => tags.includes(tag)))
console.log(result)