QTreeWidget, как и другие представления элементов, являющиеся потомками QAbstractItemView, не осведомлены о своем содержимом, поэтому они обычно используют подсказку о минимальном размере для размера виджета по умолчанию и в конечном итоге могут сами изменить размер (обычно путем расширения, если есть свободное место).
QComboBox, с другой стороны, имеет свойство sizeAdjustPolicy
, которое предоставляет подсказку другого размера в соответствии с содержимым его внутренней модели.
Значение по умолчанию для этого свойства - AdjustToContentsOnFirstShow
, что заставляет виджет перемещаться по всему содержимому модели, чтобы найти наибольший размер элемента, и использовать этот размер для подсказки размера, как только в комбинированном списке отображается first time.
Чтобы получить каждый размер элемента, Qt использует QItemDelegate, который инициализируется для каждого элемента, вычисляет размер текста, добавляет значок (если он существует) и необходимый интервал между значком и текстом, и настраивает его на полях делегата. Как вы можете себе представить, выполнение этого процесса для большого количества элементов требует много времени.
Поскольку документация для значения AdjustToMinimumContentsLengthWithIcon
сообщает:
Поле со списком откорректируется до минимальной длины содержимого плюс место для значка. По соображениям производительности используйте эту политику для больших моделей.
Как только вы установите для свойства политики это значение, вычисление размера, описанное выше, не произойдет, и виджет будет будет отображаться мгновенно.
Конечно, недостатком этого является то, что если комбо находится в очень маленьком окне или в макете, который содержит другой виджет, который требует больше места, он будет очень маленьким, возможно, не даже вообще не отображать текстовое содержимое.
Чтобы предотвратить это, вы можете установить произвольную минимальную ширину для комбинированного списка на основе текста элемента; не будет идеально (так как Qt добавляет некоторые поля вокруг текста, и вам также следует учитывать стрелку вниз), но это будет намного быстрее.
Обратите внимание, что в зависимости от шрифта, это может дать неожиданный результат, так как я использую max
против длины строки, а не фактической ширины шрифта: строка с 8 «i» будет считаться больше, чем строка с 7 «w», но последняя будет вероятно, больше, если вы не используете моноширинные шрифты.
combo = QComboBox()
combo.setSizeAdjustPolicy(combo.AdjustToMinimumContentsLengthWithIcon)
combo.addItems(items)
# use font metrics to obtain the pixel width of the (possibly) longest
# text in the list;
textWidth = self.fontMetrics().width(max(items))
# add some arbitrary margin
combo.setMinimumWidth(textWidth + 20)