Название: Рисование поверх дочерних виджетов Отправлено: Igors от Май 28, 2016, 19:11 Добрый день
Есть виджет, в нем layout в котором чайлд виджеты соединенные "проводами". И вот эти провода надо рисовать поверх чайлдов, иначе возникают непонятки. Делать провода тоже виджетами - дороговато и бестолково. Ладно, ознакомился здесь (http://www.wiki.crossplatform.ru/index.php/%D0%A0%D0%B8%D1%81%D0%BE%D0%B2%D0%B0%D0%BD%D0%B8%D0%B5_%D0%BF%D0%BE%D0%B2%D0%B5%D1%80%D1%85_%D0%B4%D0%BE%D1%87%D0%B5%D1%80%D0%BD%D0%B8%D1%85_%D0%B2%D0%B8%D0%B4%D0%B6%D0%B5%D1%82%D0%BE%D0%B2). Все ясно, наверное и работать будет - но ведь это все-таки неграмотно повторять и повторять рисование парента для каждого чайлда которых сотни. Ну а как грамотно? Спасибо Название: Re: Рисование поверх дочерних виджетов Отправлено: Bepec от Май 28, 2016, 23:26 Мы это уже проходили. Виджет стекло, на котором вы будете рисовать линии, не заморачиваясь "а где" "а что" "а когда".
Данные об детях есть, координаты начала-конца линий есть, рисуй не хочу. Название: Re: Рисование поверх дочерних виджетов Отправлено: Racheengel от Май 29, 2016, 00:42 Я бы делал через QGraphicsScene.
В статье какой-то хак описан, не факт, что будет везде работать... Название: Re: Рисование поверх дочерних виджетов Отправлено: Igors от Май 29, 2016, 07:15 Мы это уже проходили. Виджет стекло, на котором вы будете рисовать линии, не заморачиваясь "а где" "а что" "а когда". Смотрел вчера. Точнее открыл хедер - и быстренько закрылДанные об детях есть, координаты начала-конца линий есть, рисуй не хочу. Цитата: cpp #ifndef SBGLASS_H Что-то явно "не то"#define SBGLASS_H /* **************************************** [5/22/2013 Bepec]Специально для prog.org.ru Часть кода взята из статьи "Qt. Накрываем виджеты стеклом" (http://www.quizful.net/post/glass-qt-component) **************************************** */ #include <QObject> #include <QLabel> #include <QMovie> #include <QEvent> #include <QBrush> #include <QDebug> #include <QGraphicsOpacityEffect> class SBGlass : public QObject { Q_OBJECT public: SBGlass(QObject *parent = 0); ~SBGlass(); virtual void install(QWidget* w); virtual void remove(); void enableColor(const QColor& color = QColor(111, 111, 100)); void disableColor(); void enableOpacity(qreal opacity = 0.5); void disableOpacity(); void enableInfoBlock(QMovie* movie = 0, const QString& text = QString::null); void disableInfoBlock(); void enableAnimationBlock(QMovie* movie = 0); void disableAnimationBlock(); void enableInfoTextBlock(const QString& text = QString::null); void disableInfoTextBlock(); QLabel& getInfoTextBlock(); void setMovie(QMovie* movie); protected: bool eventFilter(QObject* object, QEvent* event); private: void showInfoTextBlock(const QString& text = QString::null); void showAnimationBlock(QMovie* movie = 0); void infoBlockPositioning(); private: QLabel* wGlass_; QLabel* wAnimationContainer_; QLabel* wInfoTextContaiter_; QMovie* movie_; QMovie* defaultMovie_; QColor glassColor_; bool flagInfoTextBlockEnabled_; bool flagAnimationBlockEnabled_; }; #endif // SBGLASS_H Название: Re: Рисование поверх дочерних виджетов Отправлено: Igors от Май 29, 2016, 07:20 Я бы делал через QGraphicsScene. Эти классы всегда казались мне воплощением тупости (возможно я не объективен)В статье какой-то хак описан, не факт, что будет везде работать... Рисование "foreground" - нормальная вещь/практика, должно делаться просто и естественно, без всяких хаков.Ладно, разберусь - отпишусь. Название: Re: Рисование поверх дочерних виджетов Отправлено: Bepec от Май 29, 2016, 09:58 Не нравится - не пользуйтесь, однако функцию свою он выполняет.
По поводу тупости - покажите мне, непрофессионалу, как надо сделать такой класс. Мне будет очень интересно. PS почему "не то"? Вы уж если критикуйте, то с аргументами. А то на пустозвона похожи, да и какой вы тогда профессионал, если не наставляете молодых да ранних :) Название: Re: Рисование поверх дочерних виджетов Отправлено: Racheengel от Май 29, 2016, 11:33 Верес, честно говоря, по интерфейсу класса не понятно, как с его помощью можно выполнять кастомное рисование?
Там можно только показать текст и видео проиграть, но нигде нет доступа к паинтеру. Название: Re: Рисование поверх дочерних виджетов Отправлено: Igors от Май 29, 2016, 11:51 PS почему "не то"? Вы уж если критикуйте, то с аргументами. Вот вверху Ваш хедер - какие-то QMovie, infoBlock и др. Разбираться где в этой куче "рациональное зерно" - нафиг нужно. ..мне, непрофессионалу, "Профессионал" - совсем не значит "крутой" (как часто думают). Насколько мне известно, Вы зарабатываете на жизнь программированием - стало быть, Вы профессионал. А вот какой: хороший или хреновый - это уже др вопрос :).. если не наставляете молодых да ранних :) Так это запросто (аттач)Название: Re: Рисование поверх дочерних виджетов Отправлено: Bepec от Май 30, 2016, 20:07 Видимой мудрости в исходнике не вижу. А я надеялся :)
И да, критика проекта "закрывает виджет и отображает текстовый блок и гифку" по теме "он не рисует поверх виджета", это ммм... это несколько несуразно, не находите? :P Название: Re: Рисование поверх дочерних виджетов Отправлено: Racheengel от Май 30, 2016, 21:33 И да, критика проекта "закрывает виджет и отображает текстовый блок и гифку" по теме "он не рисует поверх виджета", это ммм... это несколько несуразно, не находите? :P Это не критика скорее, а вопрос, как данное решение соответствует требованию рисования поверх виджета? Вот смотрим публичный интерфейс: Код: SBGlass(QObject *parent = 0); ЧТО здесь должен вызвать пользователь, чтобы нарисовать несколько линий? или хотя бы получить доступ к виджету-"закрывашке"? Название: Re: Рисование поверх дочерних виджетов Отправлено: Bepec от Май 31, 2016, 08:18 Igors, Racheengel - будьте внимательнее пожалуйста :)
Ни разу я не говорил о виджете, который был выложен мной на форуме. Его задача в другом - затемнять и показывать индикатор загрузки с текстом. Точка. Виджет стекло я упоминал как концепцию, а не готовое решение. Вы уж не придумывайте того, чего нет :D PS а по поводу того, что проходили - в одной из тем Igors уже задавался этим вопросом. И вот в той далекой теме с каким то названием лежит класс для рисования поверх ) с той же концепцией виджет стекло :) Название: Re: Рисование поверх дочерних виджетов Отправлено: Igors от Май 31, 2016, 13:04 PS а по поводу того, что проходили - в одной из тем Igors уже задавался этим вопросом. И вот в той далекой теме с каким то названием лежит класс для рисования поверх ) с той же концепцией виджет стекло :) Там речь была совсем о другом - рисовать "синхронно".Видимой мудрости в исходнике не вижу. А я надеялся :) В чем же по-Вашему "мудрость"? :) Ну или "что Вы ожидали увидеть?"Возвращаясь к теме: а ведь все не так уж просто как может показаться, тут есть о чем поговорить. Я реализовал простую конструкцию Парент (здесь viewport) - чайлд 1 "содержимое" (то что накрываем), часто имеет много своих чайлдов - чайлд 2 "верхний слой" (стекло) имеет WA_TranslucentBackground Осталоcь только обеспечить чтобы стекло покрывало все что нужно - и "voila". Ведь виджеты рисуются в нужном порядке. Но не тут-то было :) Оказывается такое стекло можно разбить: - в примере уберите вызов update и запустите - тыкните 1 раз в скролл бар - левая часть стекла исчезает (Qt 5.4.2) После неск часов изучения исходников мне так и не удалось понять почему так. Может просто буги-вуги? Ладно, залатал Название: Re: Рисование поверх дочерних виджетов Отправлено: GreatSnake от Май 31, 2016, 15:06 Вот работающий, правда с некоторыми хинтами, вариант
Код
Перегрузите GridManager::drawOverChild() и уже поверх чайлда рисуйте всё что хотите. Название: Re: Рисование поверх дочерних виджетов Отправлено: Igors от Июнь 01, 2016, 08:19 Вот работающий, правда с некоторыми хинтами, вариант Это близко к приводимой статье, по существу эффект тот же как унаследоваться от чайлда и перекрыть его paintEvent. Предложу еще один способКод Но это решает проблему с одним чайлдом, мне же хотелось бы создать "слой" и рисовать его один раз, не заботясь сколько чего "под ним" Название: Re: Рисование поверх дочерних виджетов Отправлено: GreatSnake от Июнь 01, 2016, 10:55 Это близко к приводимой статье, по существу эффект тот же как унаследоваться от чайлда и перекрыть его paintEvent. Предложу еще один способ Сей способ в отличие от моего не решает такой запрос: - чайлд 1 "содержимое" (то что накрываем), часто имеет много своих чайлдов Но это решает проблему с одним чайлдом, мне же хотелось бы создать "слой" и рисовать его один раз, не заботясь сколько чего "под ним" И придётся много заморачиваться с доставкой событий чайлдам, если они интерактивные.Название: Re: Рисование поверх дочерних виджетов Отправлено: Igors от Июнь 01, 2016, 17:44 Сей способ в отличие от моего не решает такой запрос: Если имеется ввиду флажок QWidget::DrawChildren - то нарисовать весь "нижний слой" одним вызовом render все равно не удается, еще чайлды будут рисоваться |