Выгрузка значений из нескольких ipywidget в контейнер - PullRequest
0 голосов
/ 15 апреля 2020

Я только начал использовать ipywidgets, и я пытаюсь найти веревки, поэтому, если на этот вопрос уже был дан ответ или документация каким-то образом его охватывает, пожалуйста, укажите мне на этот раздел. По сути, вот миниатюрная версия пользовательского интерфейса, который я пытаюсь разработать.

Вопрос, который меня озадачил, состоит в том, как только я создаю пользовательский интерфейс, как показано ниже, и пользователь предоставляет свои данные, как мне это сделать? выгрузить вход? Я надеюсь собрать значения для каждой из переменных и вызвать мои логи c, но единственное, что я вижу в документации, говорит об использовании интерактивного или интерактивного.

Однако я не совсем уверен, как используйте их с несколькими виджетами, все примеры, с которыми я сталкивался, указывают на использование их с одним виджетом. Если бы кто-нибудь мог указать мне хороший ресурс или предоставить образец, это было бы полезно.

С этим классификатором вот что я пытаюсь сделать:

import ipywidgets as widgets
style = {'description_width': 'initial'}

def input_tab(tab_list, tab_names_list):
    if len(tab_list) == len(tab_names_list):
        this_tab = Tab()
        this_tab.children = tab_list
        [this_tab.set_title(i, title) for i, title in enumerate(tab_names_list)]
        return this_tab
    else:
        raise ValueError('\n Input lists should be of the same size')

def get_input_panel_num():
    input_1 = widgets.Text(value='3000', description='Input-1', style=style)
    input_2 = widgets.Dropdown(options=['yes', 'no'], description='Select one', value='yes', disabled=False, style=style)
    input_3 = widgets.IntSlider(value=0, min=0, max=1, step=1, description='Input-3', orientation='horizontal', readout=True, 
                               style=style)
    input_list_num = [input_1, input_2, input_3]
    return input_list_num

def get_input_panel_char():
    input_a = widgets.Text(value='3000', description='Input-1', style=style)
    input_b = widgets.Dropdown(options=['yes', 'no'], description='Select one', value='yes', disabled=False, style=style)
    input_c = widgets.IntSlider(value=0, min=0, max=1, step=1, description='Input-3', orientation='horizontal', readout=True, 
                               style=style)
    input_list_char = [input_a, input_b, input_c]
    return input_list_char

def create_master_tab():
    tab_names = ["tab-1", "tab-2"]
    panel_num = VBox(get_input_panel_num())
    panel_char = VBox(get_input_panel_char())
    final = input_tab(tab_list=[panel_num, panel_char], tab_names_list=tab_names)
    return final

demo = create_master_tab()
demo 

*** ************** ОБНОВЛЕННЫЙ ВОПРОС ***************************** @ ac24: Я был Не удалось опубликовать весь код в комментариях, так что вот мой обновленный код после включения вашего совета. Он работает, как и ожидалось, по большей части, но отказывается принимать названия, что меня смущает. Мне удалось установить заголовки вкладок, когда они были функциями, используя точно такой же подход, поэтому я не уверен, что действительно изменилось:

import ipywidgets as widgets 
from ipywidgets import HBox
from ipywidgets import Tab 


# Definition of style
style = {'description_width': 'initial'}


class TabHolder(Tab):
    def __init__(self, tab_objects, tab_names):
        """
        Initialization of TabHolder object class

        :param list tab_objects: collection of display objects to be captured in the tabs
        :param list tab_names: names to assign to the tabs
        :return: tab widget containing all the tabs
        :rtype: Tab
        """

        if len(tab_names) != len(tab_objects):
            raise ValueError("\n Failed in TabHolder creation, because of lengths of inputs don't match")
        else:
            self.tab = Tab()
            self.tab_names = tab_names
            self.tab_objects = tab_objects
            self.inputs = []
            for i in tab_objects:
                self.inputs.append(i)
            super().__init__(children=self.inputs)
            [self.tab.set_title(i, title) for i, title in enumerate(self.tab_names)]  # Why titles not being set?


class InputPanelChar(HBox):

    def __init__(self):
        self.input_a = widgets.Text(value='3000', description='Input-1', style=style)
        self.input_b = widgets.Dropdown(options=['yes', 'no'], description='Select one', value='yes', disabled=False,
                                        style=style)
        self.input_c = widgets.IntSlider(value=0, min=0, max=1, step=1, description='Input-3', orientation='horizontal',
                                         readout=True, style=style)
        self.input_list_char = [self.input_a, self.input_b, self.input_c]
        super().__init__(children= self.input_list_char)

    def get_interact_value(self):
        return {
            w.description: w.get_interact_value()
            for w in self.input_list_char
        }


class InputPanelNum(HBox):

    def __init__(self):
        self.input_1 = widgets.Text(value='3000', description='Input-1', style=style)
        self.input_2 = widgets.Dropdown(options=['yes', 'no'], description='Select one', value='yes', disabled=False,
                                        style=style)
        self.input_3 = widgets.IntSlider(value=0, min=0, max=1, step=1, description='Input-3', orientation='horizontal',
                                         readout=True, style=style)
        self.input_list_num = [self.input_1, self.input_2, self.input_3]
        super().__init__(children= self.input_list_num)

    def get_interact_value(self):
        return {
            w.description: w.get_interact_value()
            for w in self.input_list_num
        }

1 Ответ

1 голос
/ 15 апреля 2020

Пройдя через точно такую ​​же проблему, я решил разработать классы групп виджетов, которые имеют смысл вместе.

Если вы преобразуете свои различные функции в классы, вы можете извлечь различные значения виджета. Я адаптировал вашу input_panel_char функцию в подкласс HBox.

Я предположил, что вы хотите получить значения виджета в виде словаря с описанием виджета в качестве ключа.

class InputPanelChar(widgets.HBox):

    def __init__(self):
        self.input_a = widgets.Text(value='3000', description='Input-1', style=style)
        self.input_b = widgets.Dropdown(options=['yes', 'no'], description='Select one', value='yes', disabled=False, style=style)
        self.input_c = widgets.IntSlider(value=0, min=0, max=1, step=1, description='Input-3', orientation='horizontal', readout=True, 
                               style=style)
        self.input_list_char = [self.input_a, self.input_b, self.input_c]
        super().__init__(children= self.input_list_char)

    def get_interact_value(self):
        return {
            w.description: w.get_interact_value()
            for w in self.input_list_char
        }

enter image description here

***** ОБНОВЛЕНИЕ *****

При создании держателя вкладок вы создаете подкласс Tab И создаете экземпляр вкладки , что вызывает путаницу. Все, что вам нужно сделать, это подкласс Tab, а затем self - это экземпляр Tab, нет необходимости создавать self.tabs в вашем экземпляре. Надеюсь, этот пример понятен:


class TabHolder(Tab):
    def __init__(self, tab_objects, tab_names):

        if len(tab_names) != len(tab_objects):
            raise ValueError("\n Failed in TabHolder creation, because of lengths of inputs don't match")
        else:
            self.tab_names = list(tab_names)
            self.tab_objects = list(tab_objects)
            super().__init__(children=self.tab_objects)
            for i, title in enumerate(self.tab_names):
                self.set_title(i, title)
...