51 |
51 |
52 class QFocusFramePrivate : public QWidgetPrivate |
52 class QFocusFramePrivate : public QWidgetPrivate |
53 { |
53 { |
54 Q_DECLARE_PUBLIC(QFocusFrame) |
54 Q_DECLARE_PUBLIC(QFocusFrame) |
55 QWidget *widget; |
55 QWidget *widget; |
56 |
56 QWidget *frameParent; |
|
57 bool showFrameAboveWidget; |
57 public: |
58 public: |
58 QFocusFramePrivate() { |
59 QFocusFramePrivate() { |
59 widget = 0; |
60 widget = 0; |
|
61 frameParent = 0; |
60 sendChildEvents = false; |
62 sendChildEvents = false; |
|
63 showFrameAboveWidget = false; |
61 } |
64 } |
62 void updateSize(); |
65 void updateSize(); |
63 void update(); |
66 void update(); |
64 }; |
67 }; |
65 |
68 |
66 void QFocusFramePrivate::update() |
69 void QFocusFramePrivate::update() |
67 { |
70 { |
68 Q_Q(QFocusFrame); |
71 Q_Q(QFocusFrame); |
69 q->setParent(widget->parentWidget()); |
72 q->setParent(frameParent); |
70 updateSize(); |
73 updateSize(); |
71 if (q->parentWidget()->rect().intersects(q->geometry())) { |
74 if (q->parentWidget()->rect().intersects(q->geometry())) { |
72 if (q->style()->styleHint(QStyle::SH_FocusFrame_AboveWidget, 0, q)) |
75 if (showFrameAboveWidget) |
73 q->raise(); |
76 q->raise(); |
74 else |
77 else |
75 q->stackUnder(widget); |
78 q->stackUnder(widget); |
76 q->show(); |
79 q->show(); |
77 } else { |
80 } else { |
82 void QFocusFramePrivate::updateSize() |
85 void QFocusFramePrivate::updateSize() |
83 { |
86 { |
84 Q_Q(QFocusFrame); |
87 Q_Q(QFocusFrame); |
85 int vmargin = q->style()->pixelMetric(QStyle::PM_FocusFrameVMargin), |
88 int vmargin = q->style()->pixelMetric(QStyle::PM_FocusFrameVMargin), |
86 hmargin = q->style()->pixelMetric(QStyle::PM_FocusFrameHMargin); |
89 hmargin = q->style()->pixelMetric(QStyle::PM_FocusFrameHMargin); |
87 QRect geom(widget->x()-hmargin, widget->y()-vmargin, |
90 QPoint pos(widget->x(), widget->y()); |
|
91 if (q->parentWidget() != widget->parentWidget()) |
|
92 pos = widget->parentWidget()->mapTo(q->parentWidget(), pos); |
|
93 QRect geom(pos.x()-hmargin, pos.y()-vmargin, |
88 widget->width()+(hmargin*2), widget->height()+(vmargin*2)); |
94 widget->width()+(hmargin*2), widget->height()+(vmargin*2)); |
89 if(q->geometry() == geom) |
95 if(q->geometry() == geom) |
90 return; |
96 return; |
91 |
97 |
92 q->setGeometry(geom); |
98 q->setGeometry(geom); |
174 |
180 |
175 void |
181 void |
176 QFocusFrame::setWidget(QWidget *widget) |
182 QFocusFrame::setWidget(QWidget *widget) |
177 { |
183 { |
178 Q_D(QFocusFrame); |
184 Q_D(QFocusFrame); |
179 if(widget == d->widget) |
185 |
|
186 if (style()->styleHint(QStyle::SH_FocusFrame_AboveWidget, 0, this)) |
|
187 d->showFrameAboveWidget = true; |
|
188 else |
|
189 d->showFrameAboveWidget = false; |
|
190 |
|
191 if (widget == d->widget) |
180 return; |
192 return; |
181 |
193 if (d->widget) { |
182 if(d->widget) |
194 // Remove event filters from the widget hierarchy. |
183 d->widget->removeEventFilter(this); |
195 QWidget *p = d->widget; |
184 if(widget && !widget->isWindow() && widget->parentWidget()->windowType() != Qt::SubWindow) { |
196 do { |
|
197 p->removeEventFilter(this); |
|
198 if (!d->showFrameAboveWidget || p == d->frameParent) |
|
199 break; |
|
200 p = p->parentWidget(); |
|
201 }while (p); |
|
202 } |
|
203 if (widget && !widget->isWindow() && widget->parentWidget()->windowType() != Qt::SubWindow) { |
185 d->widget = widget; |
204 d->widget = widget; |
186 widget->installEventFilter(this); |
205 d->widget->installEventFilter(this); |
|
206 QWidget *p = widget->parentWidget(); |
|
207 QWidget *prev = 0; |
|
208 if (d->showFrameAboveWidget) { |
|
209 // Find the right parent for the focus frame. |
|
210 while (p) { |
|
211 // Traverse the hirerarchy of the 'widget' for setting event filter. |
|
212 // During this if come across toolbar or a top level, use that |
|
213 // as the parent for the focus frame. If we find a scroll area |
|
214 // use its viewport as the parent. |
|
215 bool isScrollArea = false; |
|
216 if (p->isWindow() || p->inherits("QToolBar") || (isScrollArea = p->inherits("QAbstractScrollArea"))) { |
|
217 d->frameParent = p; |
|
218 // The previous one in the hierarchy will be the viewport. |
|
219 if (prev && isScrollArea) |
|
220 d->frameParent = prev; |
|
221 break; |
|
222 } else { |
|
223 p->installEventFilter(this); |
|
224 prev = p; |
|
225 p = p->parentWidget(); |
|
226 } |
|
227 } |
|
228 } else { |
|
229 d->frameParent = p; |
|
230 } |
187 d->update(); |
231 d->update(); |
188 } else { |
232 } else { |
189 d->widget = 0; |
233 d->widget = 0; |
190 hide(); |
234 hide(); |
191 } |
235 } |
208 |
252 |
209 /*! \reimp */ |
253 /*! \reimp */ |
210 void |
254 void |
211 QFocusFrame::paintEvent(QPaintEvent *) |
255 QFocusFrame::paintEvent(QPaintEvent *) |
212 { |
256 { |
|
257 Q_D(QFocusFrame); |
213 QStylePainter p(this); |
258 QStylePainter p(this); |
214 QStyleOption option; |
259 QStyleOption option; |
215 initStyleOption(&option); |
260 initStyleOption(&option); |
|
261 int vmargin = style()->pixelMetric(QStyle::PM_FocusFrameVMargin); |
|
262 int hmargin = style()->pixelMetric(QStyle::PM_FocusFrameHMargin); |
|
263 QWidgetPrivate *wd = qt_widget_private(d->widget); |
|
264 QRect rect = wd->clipRect().adjusted(0, 0, hmargin*2, vmargin*2); |
|
265 p.setClipRect(rect); |
216 p.drawControl(QStyle::CE_FocusFrame, option); |
266 p.drawControl(QStyle::CE_FocusFrame, option); |
217 } |
267 } |
218 |
268 |
219 |
269 |
220 /*! \reimp */ |
270 /*! \reimp */ |