How can I create multiple dropdown menus in Observable where each selection dynamically filters and limits the options available in the other dropdowns?
<!-- Load data first -->
```js
const rawData = await FileAttachment("data/raw_data.json").json();
mutable filteredData = rawData
```
```js
function getFilteredData(data, countries, languages, scopes, organizations) {
return data.filter(d => {
const countryMatch = countries.includes("All") || countries.includes(d["Country"]);
const languageMatch = languages.includes("All") || languages.includes(d["Language"]);
const scopeMatch = scopes.includes("All") || scopes.includes(d["Scope"]);
const orgMatch = organizations.includes("All") || organizations.includes(d["Rights_Holder"]);
return countryMatch && languageMatch && scopeMatch && orgMatch;
});
}
const allCountries = ["All", ...new Set(filteredData.map(d => d["Country"]))].sort();
const countriesFilter =
Inputs.select(allCountries, {
label: "Country",
value: ["All"],
multiple: 3,
width: "100%"
})
const selectedCountries = Generators.input(countriesFilter);
const languageOptions = ["All", ...new Set(filteredData.map(d => d["Language"]))].sort();
const languagesFilter =
Inputs.select(languageOptions, {
label: "Language",
value: ["All"],
multiple: 3,
width: "100%"
})
const selectedLanguages = Generators.input(languagesFilter);
const allOrganizations = ["All", ...new Set(filteredData.map(d => d["Rights_Holder"]))].sort();
const orgsFilter =
Inputs.select(allOrganizations, {
label: "Organization",
value: ["All"],
multiple: 3,
width: "100%"
})
const selectedOrganizations = Generators.input(orgsFilter);
const allScopes = ["All", ...new Set(filteredData.map(d => d["Scope"]))].sort();
const scopeFilter =
Inputs.select(allScopes, {
label: "Scope",
value: ["All"],
multiple: 3,
width: "100%"
})
const selectedScopes = Generators.input(scopeFilter);
```
```js
console.log(filteredData, selectedCountries, selectedLanguages, selectedScopes, selectedOrganizations)
filteredData = getFilteredData(filteredData, selectedCountries, selectedLanguages, selectedScopes, selectedOrganizations)
```
<div class="grid grid-cols-4">
${countriesFilter}
${languagesFilter}
${scopeFilter}
${orgsFilter}
</div>
<div class="card">
${display(Inputs.table(filteredData, {
columns: [
"Language",
"ISO",
"Country",
"Name (Common)",
"Scope",
"Rights Holder",
"Entry",
"Date Archived",
"Date Updated",
"C"
],
header:
width: {Name (Common): 200},
))}
</div>