Skip to content

Commit

Permalink
QMacStyle: Make helper-NSViews layer-backed
Browse files Browse the repository at this point in the history
This prevents the view from triggering display of its superview when
being temporarily added, which is both inefficient and causes issues
when those dirty-rects are wrong due to the wrong frame position of
the added view.

The additional drawRect: calls and corresponding expose events
resulting from the needsDisplay calls also caused repaint issues
in Qt Widgets. QWidgetBackingStore doesn't seem to take the exposed
region into account for an expose event, and will try to flush all
dirty regions. Some of those may be outside the exposed region,
and will be clipped away by the window system, never ending up on
the screen, but with Widgets still thinking it has flushed all
dirty regions.

This is a separate issue, possibly solvable by setting the
wantsDefaultClipping property on NSView to NO, but this needs
further testing, so applying this commit as workaround makes
sense, even if it's just hiding the real bug.

Task-number: QTBUG-67998
Task-number: QTBUG-68023
Task-number: QTBUG-69990
Task-number: QTBUG-69740
Task-number: QTBUG-69292
Task-number: QTBUG-69332
Reviewed-by: Timur Pocheptsov <[email protected]>
(cherry picked from commit 3897933)
Change-Id: I4ef3fef29f749daa4f3a11fe9186ae77b359f966
Reviewed-by: Simon Hausmann <[email protected]>
Reviewed-by: Morten Johan Sørvig <[email protected]>
  • Loading branch information
torarnv committed Aug 28, 2018
1 parent ac5e617 commit 2ef5362
Showing 1 changed file with 31 additions and 5 deletions.
36 changes: 31 additions & 5 deletions src/plugins/styles/mac/qmacstyle_mac.mm
Original file line number Diff line number Diff line change
Expand Up @@ -1880,20 +1880,46 @@ Carbon draws comboboxes (and other views) outside the rect given as argument. Us
return cell;
}

void QMacStylePrivate::drawNSViewInRect(NSView *view, const QRectF &qtRect, QPainter *p,
void QMacStylePrivate::drawNSViewInRect(NSView *view, const QRectF &rect, QPainter *p,
__attribute__((noescape)) DrawRectBlock drawRectBlock) const
{
QMacCGContext ctx(p);
setupNSGraphicsContext(ctx, YES);

const CGRect rect = qtRect.toCGRect();
// FIXME: The rect that we get in is relative to the widget that we're drawing
// style on behalf of, and doesn't take into account the offset of that widget
// to the widget that owns the backingstore, which we are placing the native
// view into below. This means most of the views are placed in the upper left
// corner of backingStoreNSView, which does not map to where the actual widget
// is, and which may cause problems such as triggering a setNeedsDisplay of the
// backingStoreNSView for the wrong rect. We work around this by making the view
// layer-backed, which prevents triggering display of the backingStoreNSView, but
// but there may be other issues lurking here due to the wrong position. QTBUG-68023
view.wantsLayer = YES;

// FIXME: We are also setting the frame of the incoming view a lot at the call
// sites of this function, making it unclear who's actually responsible for
// maintaining the size and position of the view. In theory the call sites
// should ensure the _size_ of the view is correct, and then let this code
// take care of _positioning_ the view at the right place inside backingStoreNSView.
// For now we pass on the rect as is, to prevent any regressions until this
// can be investigated properly.
view.frame = rect.toCGRect();

[backingStoreNSView addSubview:view];
view.frame = rect;

// FIXME: Based on the code below, this method isn't drawing an NSView into
// a rect, it's drawing _part of the NSView_, defined by the incoming clip
// or dirty rect, into the current graphics context. We're doing some manual
// translations at the call sites that would indicate that this relationship
// is a bit fuzzy.
const CGRect dirtyRect = rect.toCGRect();

if (drawRectBlock)
drawRectBlock(ctx, rect);
drawRectBlock(ctx, dirtyRect);
else
[view drawRect:rect];
[view drawRect:dirtyRect];

[view removeFromSuperviewWithoutNeedingDisplay];

restoreNSGraphicsContext(ctx);
Expand Down

0 comments on commit 2ef5362

Please sign in to comment.