Python GTK3 — Программа для выбора узла в TreeView после поиска?

#python-3.x #gtk3 #gtktreeview

Вопрос:

У меня есть функция класса, которая выполняет итерацию в Gtk.TreeStore поиске дочернего узла. Если соответствующий узел найден, я хочу изменить выбор на этот узел. Моя функция возвращает итератор. Я подозреваю, что это корень проблемы, но я не уверен, что еще можно вернуть. Все Gtk.TreeSelection функции, похоже, хотят a Gtk.TreePath .

Существует ли канонический способ найти узел в дереве, а затем выбрать его? Похоже, это распространенный вариант использования, но я, похоже, не могу найти объяснения.

 def findNodeByDescription( self, desc ):
    root_iterator = self.tree_store.get_iter_first()
    return self.findNodeByDescriptionRecursive( root_iterator, desc )

def findNodeByDescriptionRecursive( self, tree_iter, desc ):
    """ Recursive function to search the tree """
    result = None
    tree_model = self.tree_view.get_model()
    while ( result == None and tree_iter != None ):
        # is it this node?
        if ( tree_model.get_value(tree_iter, 0).description == desc ):
            # found it
            result = tree_iter 
            break
        elif ( self.tree_store.iter_has_child( tree_iter ) ):
            child_iter = self.tree_store.iter_children( tree_iter )
            result = self.findNodeByDescriptionWorker( child_iter, desc )
        tree_iter = self.tree_store.iter_next( tree_iter )
    return result
 

(ПРИМЕЧАНИЕ: я использую пользовательские узлы дерева)

Это называется как:

РЕДАКТИРОВАТЬ: Я нашел частичный get_path() ответ в функции из часто задаваемых вопросов Python GTK.

EDIT2: Использование expand_to_path() расширяет узел дерева. Я думаю, что раньше он расширял дочерний узел, но не родительский. Таким образом, он был расширен, но все еще не был виден. (У меня есть 3-глубокие ветви, и я нахожу «среднюю» ветвь).

 def findAndSelectNode( self, text ):
    tree_iter = self.findNodeByDescription( text )
    if ( tree_iter != None ):
        print("###### SELECTING ROW" )
        # THIS EXECUTES, BUT NOTHING HAPPENS?!
        path = self.tree_store.get_path( tree_iter )
        #self.tree_view.expand_row( path, True )  -- doesn't work
        self.tree_view.expand_to_path( path )
        self.tree_view.set_cursor( path )
 

Ответ №1:

Хорошо, я все уладил.

Сначала вам нужно найти нужный элемент в дереве с помощью итератора. (Код для этого содержится в вопросе).

Как только нужный узел дерева найден, у вас остается итератор, «указывающий» на конечный узел. Чтобы выделить это в дереве, необходимо выполнить два шага:

  1. Разверните всю ветвь, в которой существует цель.
  2. Измените выделение, чтобы включить этот элемент
     def findSelectNode( self, text ):
        # BUG: Only by name for now.
        tree_iter = self.findNodeByDescription( text )
        if ( tree_iter != None ):
            print("###### SELECTING ROW" )
            path = self.tree_store.get_path( tree_iter )
            self.tree_view.expand_to_path( path )               # expand the whole branch
            self.tree_view.get_selection().select_path( path )  # select it
 

Этот ответ предполагает, что вам нужен только один выбор.