How to create dropdowns that only appear after the previous selection has been made and using data that is separated by /?

33 Views Asked by At

I want to create dropdown menus that update based on the previous selection using python widgets where the next dropdown doesn't appear until the previous is selected and the number of dropdowns are not hardcoded into the code.

For example:

Example 1: First dropdown selection: Category A Category B Next dropdown selections based on Category A selection: Category A1 Category A2 Next Dropdown Selection if A1 was selected: Category A1.1 Category A1.2

Example 2: First dropdown selection: Category A Category B Next dropdown selections based on Category B selection: Category B1 Category B2 Next Dropdown Selection if B2 was selected: Category B2.1 Category B2.2 Next Dropdown selection if B2.1 was selected: B2.1.1

Example 3: First dropdown selection: Category A Category B Next dropdown selections based on Category B selection: Category B1 Category B2 Next Dropdown Selection if B2 was selected: Category B2.1 Category B2.2 Next Dropdown selection if B2.2 was selected: B2.2.1 Next Dropdown selection if B2.2.1 was selected: B2.2.1.1

I tried the following, but it is not populating correctly.

import ipywidgets as widgets

data = {'product_id': ['p1', 'p2', 'p3', 'p4', 'p5', 'p6'],
        'categories': ['Category A/Category A1/Category A1.1',
                       'Category A/Category A1/Category A1.2',
                       'Category A/Category A2/Category A2.1',
                       'Category B/Category B1/Category B1.1/Category B1.1.1',
                       'Category B/Category B2/Category B2.1/Category B2.1.1',
                       'Category B/Category B2/Category B2.2/Category B2.2.1/Category B2.2.1.1']}

# Extract all categories from data
categories = set()
for category_path in data['categories']:
    categories.update(category_path.split('/'))

# Create a dictionary that maps each category to its parent
parent_dict = {}
for category in categories:
    parent_dict[category] = '/'.join(category.split('/')[:-1])

# Create dropdown menus
dropdowns = []
prev_dropdown = None
for category in sorted(categories):
    options = [''] + [c for c in categories if parent_dict[c] == category]
    dropdown = widgets.Dropdown(options=options)
    if prev_dropdown is not None:
        def observe_dropdown(change, prev_dropdown=prev_dropdown, dropdown=dropdown):
            prev_value = prev_dropdown.value
            if prev_value != '':
                dropdown.options = [''] + [c.split('/')[-1] for c in data['categories'] if c.startswith(prev_value+'/'+change.new+'/')]
            else:
                dropdown.options = ['']
            dropdown.value = ''
        prev_dropdown.observe(observe_dropdown, 'value')
    prev_dropdown = dropdown
    dropdowns.append(dropdown)

# Display dropdown menus
widgets.VBox(dropdowns)
0

There are 0 best solutions below