Russian Qt Forum
Ноябрь 23, 2024, 10:42 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: [1] 2   Вниз
  Печать  
Автор Тема: QComboBox и его view  (Прочитано 12081 раз)
Whiplash
Гость
« : Ноябрь 15, 2010, 17:50 »

Здравствуйте. Помогите, пожалуйста, решить такую интерфейсную проблему. Или хотя бы подскажите, с какой стороны к ней подобраться.

В общем, в программах использую стиль Cleanlooks - больше всего нравится визуально. Просто жёстко в конструкторе устанавливаю и всё, но не в этом суть.
Стиль всем хорош, кроме поведения выпадающего view у комбобокса - там не показывается полос прокрутки, а вместо них - довольно неудобные области прокрутки сверху и снизу. И, кроме того, если контента много, то этот view вываливается на весь экран. Если не очень понятно - попробуйте у себя этот стиль. Более-менее сносное поведение выпадающего виджета в стиле Plastique.
Подскажите пжалста:
1. Как трансплантировать поведение (не визуальное оформление) виджета из одного стиля в другой?
2. Как по правильному изменить поведение выпадающего виджета? Хотелось бы нормальную полосу прокрутки справа, и самое сладкое - это добавить возможность мышкой раздвигать выпадающий виджет.

Сам я со стилями практически не работал, не знаю, куда копнуть по-быстрому.
Записан
GreatSnake
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2921



Просмотр профиля
« Ответ #1 : Ноябрь 15, 2010, 18:36 »

QSizeGrip
QListView
void   QComboBox::setView ( QAbstractItemView * itemView )
virtual void QComboBox::showPopup()
Записан

Qt 5.11/4.8.7 (X11/Win)
Whiplash
Гость
« Ответ #2 : Ноябрь 16, 2010, 09:23 »

В качестве view я и так использую нестандартный для комбобокса - подключил QTreeWidget. Он руками не ресайзится - поведение точно такое же, как и у стандартного view. Попробую QSizeGrip (правда, написано, что он только для top-level окон).
Записан
GreatSnake
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2921



Просмотр профиля
« Ответ #3 : Ноябрь 16, 2010, 11:59 »

Если ваша прикладина будет работать под Х-ами, то хочу вас огорчить.
QSizeGrip не будет ресайзить drop-down list Грустный
Тролли под Х-ами задействуют NET_WM_MOVERESIZE, который не работает с окнами типа Qt:: Pоpup.
Они даже до сих пор не удосужились исправить QTBUG-11447.
Единственное решение - переопределить QSizeGrip::mousePress(), QSizeGrip::mouseMove(), QSizeGrip::mouseRelease() и самому делать ресайз popup-окна.
Записан

Qt 5.11/4.8.7 (X11/Win)
Whiplash
Гость
« Ответ #4 : Ноябрь 16, 2010, 12:19 »

Я делаю под винду пока, но фиг знает - может, когда и придётся будет запускать под иксы. Но так-то и фиг с ним, с QSizeGrip.
Так вроде более-менее разобрался. Чтобы скроллбар появился, нужно его создать Улыбающийся И созджать после того, как комбобоксу присвоен view.
Сейчас встал вопрос - как сделать так, чтобы исчезли эти прокручивающие фиговины вверху и внизу списка (я раньше думал, что это какой-то спец скроллбар, а оказалось - что нет).
В стиле Cleanlooks view у комбобокса распахивается в обе стороны так, что текущий элемент оказывается под мышкой. Это не очень удобно, но с этим можно смириться.
Но самое интересное, что я обнаружил: в стиле Plastique в выпадающем TreeView неэкспандятся/коллапсятся элементы! Правда, только после второго показа Улыбающийся Т.е. запускаем приложение, раскрываем комбобокс - там тривью - работает замечательно. Выбираем элемент, снова раскрываем комбобокс - всё, дерево мёртвое, нелья ничего ни раскрыть, ни свернуть. В cleanlooks и стандартном виндовом всё нормально. вообще чудеса какие-то.
Кстати, долго пытался победить ненормальное поведение выпадающего дерева: при нажатии на +/- выбирается этот элемент и дерево исчезает. Сначала боролся с помощью eventFilter - нифига не работало (это решение на форуме нашёл). Потом сделал следующим образом:
В конструкторе:
Код:
QObject::connect(tw, SIGNAL(itemExpanded(QTreeWidgetItem*)),this, SLOT(skipHide()));
QObject::connect(tw, SIGNAL(itemCollapsed(QTreeWidgetItem*)),this, SLOT(skipHide()));
skipHide() - слот, устанавливающий внутренню булеву переменную skipNextHide в true.

И переопределённый hidePopup:
Код:
void TreeComboBox::hidePopup()
{
    if (skipNextHide){
        skipNextHide = false;
    }
    else{
        QComboBox::hidePopup();
    }
}
Записан
GreatSnake
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2921



Просмотр профиля
« Ответ #5 : Ноябрь 16, 2010, 12:26 »

Чтобы избавиться от скроллеров переопредели QCleanlooksStyle::styleHint()
и если hint==QStyle::SH_ComboBox_Popup возвращай 0.
Записан

Qt 5.11/4.8.7 (X11/Win)
Whiplash
Гость
« Ответ #6 : Ноябрь 16, 2010, 14:56 »

Спасибо, попробую.
UPD: да, действительно работает.

Сначала мучался, пытаясь сохранить геометрию попапа (ну сохранить-то непроблема - восстановить не получилось). Потом забил - всё равно на X-ах не заработает.
« Последнее редактирование: Ноябрь 16, 2010, 16:03 от Whiplash » Записан
Whiplash
Гость
« Ответ #7 : Ноябрь 16, 2010, 17:23 »

Всё, последнюю непонятку решил. Если вдруг кто-нибудь задумает в качестве попапа у комбобокса поставить дерево, то у него неполучится тривиально установить текущий элемент в комбобоксе (из программы, имеется в виду). Т.к. у него есть только setCurrentIndex(int). Хотя, логично было бы для виджета, что поддерживает MVC, иметь метод setCurrentIndex(QModelIndex).
Так вот, что бы всё-таки установить нужный текущий элемент придётся изобразить примерно следующее.
Код:
tw->setCurrentItem(item);
setRootModelIndex(tw->currentIndex().parent());
setCurrentIndex(tw->currentIndex().row());

Я использую QTreeWidget, в item - нужный элемент дерева.

И переопределить метод showPopup():
Код:
void TreeComboBox::showPopup()
{
    setRootModelIndex(QModelIndex());
    QComboBox::showPopup();
}

Всё, я почти щаслив Улыбающийся
Записан
GreatSnake
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2921



Просмотр профиля
« Ответ #8 : Ноябрь 16, 2010, 17:27 »

Дык надо было сразу использовать QTreeView.
Записан

Qt 5.11/4.8.7 (X11/Win)
Whiplash
Гость
« Ответ #9 : Ноябрь 16, 2010, 18:07 »

Дык надо было сразу использовать QTreeView.

Да вот не пофигу, чего использовать. QTreeWidget от QTreeView отличается только наличием встроенной модели, что мне собсно и надо было. В конструкторе комбобокса я вот взял и установил модель:
Код:
setModel(tw->model());

Я думаю, использование treeview в данном случае практически не отличается от treewidget.
Записан
GreatSnake
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2921



Просмотр профиля
« Ответ #10 : Ноябрь 16, 2010, 18:24 »

Я это к тому, что если бы не связывался с QTreeWidget, то использовать setCurrentItem() не пришлось бы и всё сразу заработало.
Как показывает практика местных жителей, кто начинает залезать в дебри Qt, тот не использует Q*Widget.
Вполне возможно, что тролли тоже, поэтому для Q*Widget периодически приходится делать всякие workarounds.
Записан

Qt 5.11/4.8.7 (X11/Win)
Whiplash
Гость
« Ответ #11 : Ноябрь 17, 2010, 09:14 »

Я это к тому, что если бы не связывался с QTreeWidget, то использовать setCurrentItem() не пришлось бы и всё сразу заработало.
Как показывает практика местных жителей, кто начинает залезать в дебри Qt, тот не использует Q*Widget.
Вполне возможно, что тролли тоже, поэтому для Q*Widget периодически приходится делать всякие workarounds.

Пришлось бы использовать setCurrentIndex Улыбающийся
Я вот сейчас как раз сделаю модель и допишу класс на использование внешней модели. Почти уверен, что комбобокс будет вести себя также. Отпишусь.
Записан
Whiplash
Гость
« Ответ #12 : Ноябрь 17, 2010, 10:24 »

Ну вот, переписал. Благо, модель была уже (всмысле - раньше написана в проекте и используется). Как и предполагалось - ничего не изменилось в поведении комбобокса. Малось дополнил установку текущего индекса в комбобоксе, позволяющую обойтись без переопределения метода showPopup:
Код:
 setRootModelIndex(tv->currentIndex().parent());
 setCurrentIndex(tv->currentIndex().row());
 setRootModelIndex(QModelIndex());
Записан
GreatSnake
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 2921



Просмотр профиля
« Ответ #13 : Ноябрь 17, 2010, 10:26 »

Ну и славненько)
Записан

Qt 5.11/4.8.7 (X11/Win)
picobrain
Гость
« Ответ #14 : Ноябрь 17, 2010, 21:10 »

Гм. Спасибо всем. Тоже интересовался.
Заморачиваться не стал - если у комбобокса предполагалось больше 10-20 элементов,
выставлял ему стиль Windows.
Записан
Страниц: [1] 2   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.051 секунд. Запросов: 23.