How can I build a list from a JSON array based on a selected value?

Viewed 67

I am trying to create a filtered select list of sources based on the media selected. I know the method I used below filters but does not display the list correctly. I am half asleep and trying to correct this and need some input from someone. :-) Cheers!

let types = [
  {
    "id": 1,
    "media": "TV",
    "source": "wkbw"
  },
  {
    "id": 2,
    "media": "TV",
    "source": "wffo"
  },
  {
    "id": 3,
    "media": "TV",
    "source": "wtrw"
  },
  {
    "id": 8,
    "media": "Radio",
    "source": "wrqa"
  },
  {
    "id": 9,
    "media": "Radio",
    "source": "wuqa"
  },
  {
    "id": 10,
    "media": "Radio",
    "source": "wzzt"
  }
]

$("#type").change(function() {
    $("#results").empty();
    selected = $("#type").val();
  
  for (var i = 0; i < types.length; i++) {
    // some kind of filter source by selected the one below isn't quite right
    // $("#results").append("<option value='" + types[i].source + "'>" + types[i].source + "</option>");
    source = types.filter(types => types.media === selected).map(d => d.source).join('');
    $("#results").append("<option value='" + source + "'>" + source + "</option>");
  }
});

Here is my fiddle: https://jsfiddle.net/simplymarkb/sk0rdf2j/31/

3 Answers

You have to use filter outside the loop and get the value of source[i] in the option.

Also just use .html() to empty the select again onchange.

Here you go => Working Demo: https://jsfiddle.net/usmanmunir/u38hrox1/11/

Just run snippet to see it action.

let types = [
  {
"id": 1,
"media": "TV",
"source": "wkbw"
  },
  {
"id": 2,
"media": "TV",
"source": "wffo"
  },
  {
"id": 3,
"media": "TV",
"source": "wtrw"
  },
  {
"id": 8,
"media": "Radio",
"source": "wrqa"
  },
  {
"id": 9,
"media": "Radio",
"source": "wuqa"
  },
  {
"id": 10,
"media": "Radio",
"source": "wzzt"
  }
]

$("#type").change(function() {
  $("#results").html('')
  var selected = $("#type").val();
  var source = types.filter(types => types.media === selected).map(d => d.source);
  for (var i = 0; i < source.length; i++) {
    $("#results").append("<option value='" + source[i] + "'>" + source[i] + "</option>");
  }

});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<select id="type">
  <option value="TV">TV</option>
  <option value="Radio">Radio</option>
</select>
<hr>
<select id="results">..results</select>

Just rewrite your code with a simple if statement like this:

   let types = [
  {
    "id": 1,
    "media": "TV",
    "source": "wkbw"
  },
  {
    "id": 2,
    "media": "TV",
    "source": "wffo"
  },
  {
    "id": 3,
    "media": "TV",
    "source": "wtrw"
  },
  {
    "id": 8,
    "media": "Radio",
    "source": "wrqa"
  },
  {
    "id": 9,
    "media": "Radio",
    "source": "wuqa"
  },
  {
    "id": 10,
    "media": "Radio",
    "source": "wzzt"
  }
]

$("#type").change(function() {
    $("#results").empty();
    selected = $("#type").val();
  
  for (var i = 0; i < types.length; i++) {
    if(types[i].media === selected){
      $("#results").append("<option value='" + types[i].source + 
          "'>" + types[i].source + "</option>");
    }
  }
});

Please take a look at the following solution

let types = [
  {
    id: 1,
    media: "TV",
    source: "wkbw",
  },
  {
    id: 2,
    media: "TV",
    source: "wffo",
  },
  {
    id: 3,
    media: "TV",
    source: "wtrw",
  },
  {
    id: 8,
    media: "Radio",
    source: "wrqa",
  },
  {
    id: 9,
    media: "Radio",
    source: "wuqa",
  },
  {
    id: 10,
    media: "Radio",
    source: "wzzt",
  },
];

const type = document.querySelector("#type");
const result = document.querySelector("#result");

type.addEventListener("change", changeHandler);

function changeHandler(event) {
  const output = types
    .filter((type) => type.media === event.target.value)
    .map((type) => `<option value="${type.source}">${type.source}</option>`)
    .join("");

  result.innerHTML = output;
}
  
<select name="type" id="type">
  <option value="" disabled selected>Select value</option>
  <option value="TV">TV</option>
  <option value="Radio">Radio</option>
</select>

<select name="result" id="result"></select>

<script src="app.js"></script>

Related