Название: Дырка QMessageBox Отправлено: Гурман от Ноябрь 25, 2015, 18:15 Код: QMessageBox box; Бокс не появится... . Поиски вывели на соответствующий баг в базе на bugreports.qt.io. Был подтвержден в версиях 4.8 и 5.4. Теперь еще и в 4.7. Очень странный баг, так не срабатывает именно вызов show() внутри exec(). Название: Re: Дырка QMessageBox Отправлено: Nimbus от Ноябрь 25, 2015, 22:13 Код: QMessageBox box(); Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 26, 2015, 00:33 Код: QMessageBox box(); Ничего странного, скобки лишние остались при редактировании. Убрал. К дырке это отношения не имеет. Название: Re: Дырка QMessageBox Отправлено: Bepec от Ноябрь 26, 2015, 08:20 хм... Очень интересно, а нафига такое поведение?
Всмысле что messageBox обычно идёт на всё приложение, а вы хотите его сделать отдельным для каждого виджета? Интересно, а интерфейс весь блокируется или только указанной виджет? :) Название: Re: Дырка QMessageBox Отправлено: qate от Ноябрь 26, 2015, 10:07 а так QMessageBox box(this); ?
Название: Re: Дырка QMessageBox Отправлено: GreatSnake от Ноябрь 26, 2015, 12:05 а так QMessageBox box(this); ? У меня на 5.5 так работает.При назначении родителя позже содержимое диалога рисуется прямо на окне заданного родителя. Т.е. репарент отрабатывает правильно, но с точки зрения обычного виджета, а не под-окна. хм... Очень интересно, а нафига такое поведение? +1Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 26, 2015, 17:49 хм... Очень интересно, а нафига такое поведение? Всмысле что messageBox обычно идёт на всё приложение, а вы хотите его сделать отдельным для каждого виджета? Интересно, а интерфейс весь блокируется или только указанной виджет? :) Есть окно "управления" и есть окно "данных". При необходимости окно "данных" у пользователя должно перекрываться модальным окном с сообщением. При этом разработчику должно быть доступно окно "управления", его блокировать нельзя, но разработчик должен видеть, как блокируется окно "данных", когда отлаживает решение для пользователя. Обычному пользователю окно "управления" не доступно. Всё работает как надо, если сделать Код: box = new QMessageBox( dataWindow ); Где dataWindow - окно данных. При этом box появляется по центру этого окна и блокирует только его. Все остальные окна приложения доступны. В режиме "разработки" это важно. Чтобы так сделать, пришлось немного усложнить приложение, так как dataWindow находится в одном плагине, а box в другом, и там где box, ничего про dataWindow по идее не известно. Если бы работал box->setParent( dataWindow ), тогда было бы проще - указатель на QWidget бокса передавался бы в плагин dataWindow, а там он сам умеет полученных делать своими потомками. Название: Re: Дырка QMessageBox Отправлено: GreatSnake от Ноябрь 26, 2015, 18:01 Что-то как-то уж больно сложно...
А почему бы у dataWindow не сделать метод/слот типа showMessage() ? Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 26, 2015, 18:20 Что-то как-то уж больно сложно... Так и приложение больно не простое... Это не приложение даже, а инструмент для создания приложений, типа среды разработки. Можно считать так - окно "данных", это окно "приложения". А окно "управления" - это окно "отладчика". Собственно, по сути так и есть.А почему бы у dataWindow не сделать метод/слот типа showMessage() ? Во-первых, пришлось бы повторить практически весь функционал QMessageBox. Это должно быть именно окно с сообщением, с разными иконками, звуковыми сигналами и кнопками реагирования, в разных вариантах (Neutral message, Error, Warning, Question, Info, Extended Info) - а не просто сообщение на dataWindow, тем более, что именно dataWindow является инициатором появления сообщений. То есть, не слот должен быть, а сигнал. ;-) Но реальность гораздо разнообразнее. QMessageBox же делает всё что нужно. Во-вторых, плагин с выдачей сообщения может и отсутствовать, или может в будущем иметь немного другой функционал.Название: Re: Дырка QMessageBox Отправлено: Bepec от Ноябрь 26, 2015, 21:59 Слишком замудрено, да и получается что у вас сообщение блокирующее вообще неизвестно где находится и находится ли вообще, при том оно само не в курсе что блокирует и пошто.
А на деле вы неправы. Тут как раз идёт обобщённость Qt, setParent это метод QWidget, а инициализация в конструкторе - метод QMessageBox как самостоятельного виджета. Так что вы получили правильное поведение как виджета, но неправильное как QMessageBox. Это ясно видно в асситенте. На мой взгляд всё правильно, дырок нет, просто вы недоглядели. Разобрались и ладно, я рад за вас. PS поменять общее поведение всех QWidget ради неосмотрительности программиста... Ммм, вы же баг создали? Так если не трудно держите нас в курсе, что ответят разрабы :) Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 26, 2015, 22:52 Слишком замудрено, да и получается что у вас сообщение блокирующее вообще неизвестно где находится и находится ли вообще, при том оно само не в курсе что блокирует и пошто. Не получается. Оно появляется там где надо - ровно по центру того окна, которое оно блокирует. И оно в курсе, если ему надо - оно блокирует своего родителя. Только родитель устанавливается не вызовом setParent(), а в конструкторе бокса. А на деле вы неправы. Тут как раз идёт обобщённость Qt, setParent это метод QWidget, а инициализация в конструкторе - метод QMessageBox как самостоятельного виджета. Не... То, что кувиджет прячется при смене родителя - это я в курсе. У него hidden взводится. Но он обязан появляться по методу show(). Я с этим имел дело. Однако именно бокс по show() не появляется. Вот где баг.Так что вы получили правильное поведение как виджета, но неправильное как QMessageBox. Это ясно видно в асситенте. На мой взгляд всё правильно, дырок нет, просто вы недоглядели. Разобрались и ладно, я рад за вас. PS поменять общее поведение всех QWidget ради неосмотрительности программиста... Ммм, вы же баг создали? Так если не трудно держите нас в курсе, что ответят разрабы :) Баг не я создал, он уже был на багтрекере, с прошлого года. Я только его подтвердил, причём не только я. Словесной реакции разрабов там нет. Есть только метка P2 Important и Unresolved. Баг подтвержден в 4.7.0, 4.8.0, 5.3.3, 5.4.7. То есть дырка историческая.Название: Re: Дырка QMessageBox Отправлено: Bepec от Ноябрь 27, 2015, 07:29 Ну и слава богу.
А по поводу исчезновения - предполагаю что он всё таки проходит, show, но так же быстро он и затирается основным окном :) Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 27, 2015, 12:16 Ну и слава богу. А по поводу исчезновения - предполагаю что он всё таки проходит, show, но так же быстро он и затирается основным окном :) Неа. Затертое может быть не видно, но виртуально оно присутствует. Тогда основное окно должно было бы блокироваться. Но этого не происходит. Бокс не исчезает - он не появляется. Название: Re: Дырка QMessageBox Отправлено: Bepec от Ноябрь 27, 2015, 14:30 А как он будет блокироваться, если бокс принадлежит родителю и следовательно события для родителя не перестают приходить.
Как то сумбурно думается, но ведь если он отрисовывается на окне, то и блокировка должна распространяться на окно, к которому принадлежит класс messageBox, или нет? По идее всё правильно, блокируются все события, которые идут НЕ окну messageBox. В случае если окно messageBox == окно родителя, то блокировка на него действовать не будет, не? Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 27, 2015, 14:43 В случае если окно messageBox == окно родителя, то блокировка на него действовать не будет, не? Нигде такого нет "messageBox == окно родителя". Откуда это взялось? Я устанавливаю родителем messageBox.setParent( dataWindow ). Соответственно, dataWindow по иерархии выше messageBox, и при отправке ему событий они должны упираться в блокировку, при условии что messasgeBox видим, то есть у него hidden == false. Раз события для родителя не блокируются, а messageBox не видим даже после messageBox.show(), значит у него при этом hidden == false так и осталось. Название: Re: Дырка QMessageBox Отправлено: Bepec от Ноябрь 27, 2015, 15:13 Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 27, 2015, 15:55 Покопаюсь чуток. На всякий случай - если без box->setWindowModality( Qt::WindowModal ); то бокс появляется также посередине родительского окна, но блокируется весь интерфейс приложения. Собственно, это всё описано в документации. Название: Re: Дырка QMessageBox Отправлено: Igors от Ноябрь 27, 2015, 15:58 Если нужна блокировка окна (а не приложения), то проще так
Код
Название: Re: Дырка QMessageBox Отправлено: Bepec от Ноябрь 27, 2015, 16:12 Покопался. Всё правильно работает и мой сумбур верен. Расписываю.
1) Модальность - свойство окна. Не виджета, а именно окна. При установлении родителем окна, диалог считает себя и родителя одним окном, что вполне логично, окно одно. 2) Блокировка событий. Блокировка событий использует внутри QDialog processEvents с недокументированным флагом QEventLoop::DialogExec, что вызывает свободный проход событий для ОКНА диалога. (напоминаю пункт 1 - окно то у нас одно) 3) насчёт пропадания диалога. Диалог отрисовывается на вашем окне, но изза ситуации что окно "не родное", а предка, там происходит наложение размеров рабочего стола (1920x1080) на положение окна (86*30) и размер окна (800*600), что в конечном итоге приводит в моём случае на перенос отрисовки по координатам окна с 0*0 на ~600*400. При передвижении окна чуть ближе к центру, отрисовка пропадает - уходит за границу видимой области. Так что вот утверждения. Окно диалога есть, модальность окна не сохраняется(т.к. окно родител), луп работает, но обеспечивает работоспособность окна диалога :) PS да, дополнительно проверил, qDebug() << window()->objectName(); в классе диалога выдаёт родителя при использовании setParent :) Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 27, 2015, 16:31 3) насчёт пропадания диалога. Диалог отрисовывается на вашем окне, но изза ситуации что окно "не родное", а предка, там происходит наложение размеров рабочего стола (1920x1080) на положение окна (86*30) и размер окна (800*600), что в конечном итоге приводит в моём случае на перенос отрисовки по координатам окна с 0*0 на ~600*400. При передвижении окна чуть ближе к центру, отрисовка пропадает - уходит за границу видимой области. Сие есть баг. После установки родителя, уже нельзя центрировать окно по размерам десктопа. И баг проявляется при разной последовательности действий. Если родитель задается при вызове конструктора бокса - всё работает, как ожидается. И бокс посередине родителя, и родитель под ним блокируется. То есть, при Код: QMessageBox box( (QWidget*) parent ); всё нормально. Но Код: QMessageBox box( (QWidget*) 0 ); уже другой результат. Хотя логически это одно и то же. Название: Re: Дырка QMessageBox Отправлено: Bepec от Ноябрь 27, 2015, 16:35 Не досмотрел где там точно баг, не за этим в исходники лазил. :)
Но согласен, смещение координат бага бага. Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 27, 2015, 16:41 Не досмотрел где там точно баг, не за этим в исходники лазил. :) Но согласен, смещение координат бага бага. Я даже могу почти наверняка сказать где - координаты бокса вычисляются в конструкторе, а после смены родителя не пересчитываются. ;) Название: Re: Дырка QMessageBox Отправлено: Igors от Ноябрь 27, 2015, 17:37 А как сделать наоборот - диалог блокирует все окна кроме заданного(ых)?
Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 27, 2015, 17:43 А как сделать наоборот - диалог блокирует все окна кроме заданного(ых)? Цепочкой родительские отношения блокируемым окнам установить. А не блокируемое не включать в цепочку. Правда после закрытия диалога отношения надо убирать. Специальный класс "группа окон" придётся сделать. Название: Re: Дырка QMessageBox Отправлено: GreatSnake от Ноябрь 27, 2015, 17:47 А как сделать наоборот - диалог блокирует все окна кроме заданного(ых)? Код
Название: Re: Дырка QMessageBox Отправлено: Igors от Ноябрь 28, 2015, 07:31 Код
Код Ожидается что 2 окна будут блокированы, а между 2-мя др можно переключаться. Но на Вындоуз вообще никакой модальности, а на OSX есть но для одного окна, т.е. никаких переключений. На обоих платформах QMessageBox блокирует всех ЧЯДНТ? Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 28, 2015, 18:17 ЧЯДНТ? Кто кого тут блокировать будет? У создаваемого QWidget * win = new QWidget; родителем является десктоп. А чтобы win->setWindowModality(Qt::WindowModal); работало, родителем у win должно быть другое окно. Тогда win будет его блокировать. Название: Re: Дырка QMessageBox Отправлено: Igors от Ноябрь 29, 2015, 08:56 Кто кого тут блокировать будет? У создаваемого QWidget * win = new QWidget; родителем является десктоп. А чтобы win->setWindowModality(Qt::WindowModal); работало, родителем у win должно быть другое окно. Тогда win будет его блокировать. Ну вот и показали бы кодом, а то словеса. Хорошо, делаю как я Вас понялКод На Вындоуз это работает "не вполне". Т.е. да, я могу переключаться между окнами 2 и 4. а окна 1 и 3 блокированы. Но вот почему активное окно 2 может быть свободно перекрыто неактивными - хз. А на OSX нужный ф-ционал вообще не достигается - окна 3 и 4 "вставляются" в окно 1 (Sheet окна). См аттач Видимо WindowModal здесь не решение Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 29, 2015, 14:19 QWidget - это НЕ окно. Модальность работает для окон, а не для кувиджетов. RTFM, там это описано. Тролли несколько запутали тем, что модальность задаётся у кувиджетов, потому что класса QWindow отдельного нет.
Цитировать почему активное окно 2 может быть свободно перекрыто неактивными Что тут означает "свободно перекрыто"? у окна win2 нет потомков, оно само по себе, перекрыто оно может быть кем угодно, но при этом оно не блокировано Вообще с parent/children есть запутанность. В последнем примере окну win1 придаются два потомка win3 и win4. В документации нет ни слова о том, что у окна могут быть несколько окон-потомков, на которые распространяется правило модальности. Вообще-то модальным в иерархии, может быть по определению только одно окно. Это его сущность. Поэтому попытка сделать два модальных окна для одного родителя не должна работать. Поэтому окно win3 блокируется, хотя вроде бы не должно, так как win4 не является его потомком. Насколько я понимаю, для реализации модальности используются механизмы host OS. Очевидно поэтому и в OSX работает по-другому, так как ОС не понимает чего от неё хотят. Можно сделать два модальных окна, но у каждого должен быть свой родитель. У меня сейчас модальность идентично работает в Windows и KDE Kubuntu 14 в версиях 32 и 64 бита. Цитировать показали бы кодом, а то словеса это не словеса, а описание бизнес-логики, оно первично, если оно правильно понято, то написать код - дело техникиНазвание: Re: Дырка QMessageBox Отправлено: Igors от Ноябрь 30, 2015, 10:45 ... потому что класса QWindow отдельного нет. Давным-давно есть :)Вот ситуевина. Есть плагины с UI в виде модальных окон с кнопками Ok, Cancel. Это в принципе устраивает, НО нужна возможность отрендерить preview не нажимая кнопку Ok, т.е. не выходя из UI плагтна. Ладно, добавляем горячую клавишу, по ней preview рендерится и показывается в новом окне (или в старом если preview уже вызывалось). Но это новое окно нельзя даже передвинуть - не дает окно модальное плагина И что, рассказывать юзеру что он должен сто раз жать Ok и снова открывать плагин - потому что, дескать, вообще-то модальность... Так юзера это мало волнует, ему нужно удобство Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 30, 2015, 13:12 ... потому что класса QWindow отдельного нет. Давным-давно есть :)А, и в самом деле, есть в 5.х. Но не так уж давным давно... всего-то 3 года. Так с этим классом и надо работать, а не с QWidget. У него свои методы для модальности, даже isModal() есть. Вот ситуевина. Есть плагины с UI в виде модальных окон с кнопками Ok, Cancel. Это в принципе устраивает, НО нужна возможность отрендерить preview не нажимая кнопку Ok, т.е. не выходя из UI плагтна. Ладно, добавляем горячую клавишу, по ней preview рендерится и показывается в новом окне (или в старом если preview уже вызывалось). Но это новое окно нельзя даже передвинуть - не дает окно модальное плагина Поместите кнопки Ok и Cancel руками на окно, в котором рендеринг, сделайте спрятанными, показывайте их когда рендеринг завершился, при нажатии любой скрывайте. Если окон много, сделайте, чтобы окно с рендерингом всплывало поверх всех при появлении кнопок. Можно еще "бряк" издавать, но отключаемый в настройках, всплытие тоже лучше отключаемое. Модальное окно вообще не будет нужно. Но это всё уже оффтопик.И что, рассказывать юзеру что он должен сто раз жать Ok и снова открывать плагин - потому что, дескать, вообще-то модальность... Так юзера это мало волнует, ему нужно удобство Название: Re: Дырка QMessageBox Отправлено: Igors от Ноябрь 30, 2015, 13:21 Так с этим классом и надо работать, а не с QWidget. У него свои методы для модальности, даже isModal() есть. Не вдаваясь в детали - ничего нового (по сравнению с QWidget) там не получить. Так, "выделили сущность" что в общем хорошоПоместите кнопки Ok и Cancel руками на окно, в котором рендеринг, сделайте спрятанными, показывайте их когда рендеринг завершился, при нажатии любой скрывайте. Если окон много, сделайте, чтобы окно с рендерингом всплывало поверх всех при появлении кнопок. Можно еще "бряк" издавать, но отключаемый в настройках, всплытие тоже лучше отключаемое. Модальное окно вообще не будет нужно. ??? А окно плагина куда я дену? Которое делал автор плагиеа (не я) и которое должно быть модальноНо это всё уже оффтопик. Ну да, сразу в кусты (как Верес :))Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 30, 2015, 13:42 А окно плагина куда я дену? Которое делал автор плагиеа (не я) и которое должно быть модально Если им невозможно управлять, то какой смысл вообще было задавать эти вопросы? Ну да, сразу в кусты (как Верес :)) Я могу не в кусты. Но у меня условие - в проекте я работаю только руководителем проекта, с соответствующей зарплатой. Название: Re: Дырка QMessageBox Отправлено: Bepec от Ноябрь 30, 2015, 14:08 Igors как обычно нашёл тему, которая ему неинтересна, нашёл проблему, которую ему не надо решать, и теперь пинает автора со словами - а ну реши мне ради прикола :D
Название: Re: Дырка QMessageBox Отправлено: Igors от Ноябрь 30, 2015, 14:24 Если им невозможно управлять, то какой смысл вообще было задавать эти вопросы? Так у Вас же вроде "много плагинов". Они же должны иметь какие-то настраиваемые параметры. Вот у меня по выбору из меню управление отдается плагину, и тот показывает модальный диалог где эти параметры можно редактировать. А у Вас как?Я могу не в кусты. Но у меня условие - в проекте я работаю только руководителем проекта, с соответствующей зарплатой. Ну зачем же мне руководитель проекта который не может 2 окна сделать активными? :) Такого и юниором брать не резон, какая уж тут зряплата...Igors как обычно нашёл тему, которая ему неинтересна, нашёл проблему, которую ему не надо решать, и теперь пинает автора со словами - а ну реши мне ради прикола :D А Вересу, как обычно, сорока на хвосте чего-то принесла, да он не может вспомнить что и как :)Название: Re: Дырка QMessageBox Отправлено: Гурман от Ноябрь 30, 2015, 16:32 Так у Вас же вроде "много плагинов". Они же должны иметь какие-то настраиваемые параметры. Вот у меня по выбору из меню управление отдается плагину, и тот показывает модальный диалог где эти параметры можно редактировать. А у Вас как? А у меня архитектура плагинов разработана мной, и у них есть средства для их общения - автоматически устанавливаемые при загрузке плагинов соединения через сокеты, с собственным реестром таких соединений. Плагины знают, кто когда загрузился, что можно с ним и его окнами делать (точнее попросить сделать), и т.д. И настройки у них есть, их сохраняет и восстанавливает общая среда-интегратор, в ней есть унифицированный редактор настроек. Всё заранее продуманно. Ну зачем же мне руководитель проекта который не может 2 окна сделать активными? :) Такого и юниором брать не резон, какая уж тут зряплата... Я то как раз могу ВСЁ... Но сначала контракт - потом решение. Наоборот не бывает. Название: Re: Дырка QMessageBox Отправлено: Igors от Декабрь 01, 2015, 09:57 Я то как раз могу ВСЁ... На фоне трепыханий в мелких подробностях UI такие заявления воспринимаются "наоборот" :) Но сначала контракт - потом решение. Наоборот не бывает. То есть разруливание 2 окон - серьезная проблема, ее решение должно быть обязательно подкреплено контрактом? :)Название: Re: Дырка QMessageBox Отправлено: Гурман от Декабрь 01, 2015, 12:55 То есть разруливание 2 окон - серьезная проблема, ее решение должно быть обязательно подкреплено контрактом? :) Такой глупый вопрос мог задать только тот, кто никогда не руководил проектами. Всё, закрыта тема. Если будет оффтопик дальше, закрою "физически". Название: Re: Дырка QMessageBox Отправлено: Igors от Декабрь 01, 2015, 14:47 Такой глупый вопрос мог задать только тот, кто никогда не руководил проектами. Пожалуйста командуйте у себя дома (если жена разрешит :))Всё, закрыта тема. Если будет оффтопик дальше, закрою "физически". Название: Re: Дырка QMessageBox Отправлено: lit-uriy от Декабрь 03, 2015, 07:14 Мужики, я честно скажу, тему внимательно не читал.
Но, вы не забыли, что метод QDialog::exec() (унаследованный QMessageBox-ом) делает так: Код а по завершении восстанавливает исходные свойства Название: Re: Дырка QMessageBox Отправлено: Гурман от Декабрь 03, 2015, 12:35 Мужики, я честно скажу, тему внимательно не читал. Прочитайте, заметите, что не работает даже метод show(). |